c++c++11exception-safemove-semantics

Can a stack have an exception safe method for returning and removing the top element with move semantics?


In an answer to a question about std::stack::pop() I claimed that the reason pop does not return the value is for exception safety reason (what happens if the copy constructor throws).

@Konrad commented that now with move semantics this is no longer relevant. Is this true?

AFAIK, move constructors can throw, but perhaps with noexcept it can still be achieved.

For bonus points what thread safety guarantees can this operation supply?


Solution

  • Of course, not every type is move-enabled and C++0x even allows throwing move constructors. As long as constructing the object from an rvalue may throw it cannot be exception-safe. However, move semantics allows you to have many types that are nothrow-constructible given an rvalue source.

    Conditional support for this could be done with SFINAE. But even without such a conditional member function nothing stops you from writing:

    auto stack = ...;
    auto elem = std::move_if_noexcept(stack.back());
    stack.pop_back();
    

    which is makes the strong exception guarantee even in case your move constructor doesn't give the strong guarantee.