Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

`noexcept` specifier for getters and setters

Tags:

c++

c++11

Let's say I have the following code:

class A {
    public:
        void SetInteger(const int val) noexcept { integerMember = val; }
        void SetString(const std::string& val) { stringMember = val; }
        int GetInteger() const noexcept { return integerMember; }
        std::string GetString() const { return stringMember; }

    private:
        int integerMember;
        std::string stringMember;
}

Using noexcept for integral types and pointers seems for me pretty obvious.

But what are recommendations in case of not integral types like classes and structures that do not throw exceptions in constructor/copy-constructor and constructors of their parts explicitly (meaning using throw in constructor body)?

like image 226
Alex Avatar asked May 16 '17 12:05

Alex


People also ask

When should I use Noexcept keyword?

The noexcept operator performs a compile-time check that returns true if an expression is declared to not throw any exceptions. It can be used within a function template's noexcept specifier to declare that the function will throw exceptions for some types but not others.

What is the purpose of Noexcept?

noexcept is primarily used to allow "you" to detect at compile-time if a function can throw an exception. Remember: most compilers don't emit special code for exceptions unless it actually throws something.

Does Noexcept make code faster?

If an exception is not supposed to be thrown, the program cannot be assumed to cope with the error and should be terminated as soon as possible. Declaring a function noexcept helps optimizers by reducing the number of alternative execution paths. It also speeds up the exit after failure.

Can be declared Noexcept?

C26440 DECLARE_NOEXCEPT "Function can be declared 'noexcept'." If code is not supposed to cause any exceptions, it should be marked as such by using the 'noexcept' specifier. This would help to simplify error handling on the client code side, as well as enable compiler to do additional optimizations.


3 Answers

You should avoid noexcept specifiers for functions which may throw (unless you're prepared to have your code call std::terminate()). Explicit throw specifiers are deprecated, so don't rely on them, rather use the noexcept operator. For example

template<typename T>
class Foo
{
  T m_datum;
public:
  Foo& SetDatum(T const&x) noexcept(noexcept(m_datum=x))
  {
    m_datum = x;
    return *this;
  }
};
like image 88
Walter Avatar answered Oct 05 '22 03:10

Walter


Outside of special member functions, noexcept is not that useful. But if you want it:

void SetString(const std::string& val) 
         noexcept(std::is_nothrow_copy_assignable<std::string>::value) {
}
like image 31
T.C. Avatar answered Oct 05 '22 04:10

T.C.


First way for getter:

const std::string& GetString() const noexcept {return stringMember; }

Second way is for setter:

void SetString(std::string&& val) noexcept {
    swap(stringMember, val);
}
like image 22
knst Avatar answered Oct 05 '22 02:10

knst