How to use noexcept in assignment operator with copy-and-swap idiom?

拟墨画扇 提交于 2019-12-30 00:55:15

问题


The move assignment operator should often be declared noexcept (i.e. to store the type in STL containers). But the copy-and-swap idiom allows both copy- and move- assignment operators to be defined in a single piece of code. What to do with noexcept specifier in this case? The copy construction can throw, but I doubt whether it can violate the noexcept specifier.

// Is it correct considering that T copy constructor can throw?
T& operator=(T other) noexcept;

回答1:


Since the copy is made on the caller's side of the call, it is not part of what your function does. It can therefore not be controlled by your function and consequently, you can not include this information in the noexcept specification.

The only thing you could do is to play it safe and add both options to your noexcept specification. Of course, that means you are getting some false-negatives.




回答2:


As usual, Daniel Frey is correct. All I want is showing a piece of code that illustrates the point.

#include <iostream>

struct foo {

    foo() = default;

    foo(const foo&) {
        std::cout << "throw\n";
        throw 1;
    }

    foo& operator =(foo) noexcept {
        return *this;
    }
};

int main() {

    foo f, g;
    try {
        f = g; // throws
    }
    catch(int) {
        std::cout << "catch\n";
    }
}

When compiled with gcc 4.8.1 (-std=c++11 -Wall -Wextra -pedantic) it gives no warnings. Running the code produces the following output:

throw
catch

Therefore, the copy constructor does throw when called but that's no considered inside operator =() and, therefore, the noexcept promise was fulfilled. Otherwise, terminate would be called before catch could be printed out.



来源:https://stackoverflow.com/questions/18848215/how-to-use-noexcept-in-assignment-operator-with-copy-and-swap-idiom

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!