Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Different uses of noexcept

In the book The C++ Programming Language it is written that you can declare a function to be conditionally noexcept. For example:

template<typename T>
void my_fct(T& x) noexcept(std::is_pod<T>::value);

noexcept takes a predicate that must be a constant expression (in the example std::is_pod<T>::value).

However, in the book it is also written:

The noexcept() operator takes an expression as its argument and returns true if the compiler knows that it cannot throw and false otherwise.

Taking this into account, consider:

constexpr bool f() { return true; }

void g() noexcept(f())
{
    f();
}

Is g() marked as noexcept or not? I see two possibilities:

  1. The call f() is evaluated at compile-time because it is marked constexpr, it returns true and as a result g() is marked noexcept.
  2. The compiler cannot determine that f() cannot throw an exception because f() is not marked noexcept. As a result g() is not marked noexcept.

Which one does happen? How can I select one or other behavior for noexcept?

like image 403
Roxanne Avatar asked Jan 25 '23 06:01

Roxanne


1 Answers

The language grammar allows only the noexcept specifier to appear in that position.

Therefore your first point is correct. g() will be marked noexcept, because f() returns true.

The noexcept operator must appear in an expression. The noexcept specifier takes an expression as argument, so if one wants to have a function be noexcept depending on whether a certain expression is noexcept, one has to write:

void g() noexcept(noexcept(f()))
{
    f();
}

which will behave according to your second point.

like image 101
walnut Avatar answered Feb 09 '23 06:02

walnut