What is the difference between throw and throw with arg of caught exception?

前端 未结 2 2071
清酒与你
清酒与你 2020-12-09 09:59

Imagine two similar pieces of code:

try {
  [...]
} catch (myErr &err) {
  err.append(\"More info added to error...\");
  throw err;
}

2条回答
  •  执笔经年
    2020-12-09 10:06

    Depending on how you have arranged your exception hierarchy, re-throwing an exception by naming the exception variable in the throw statement may slice the original exception object.

    A no-argument throw expression will throw the current exception object preserving its dynamic type, whereas a throw expression with an argument will throw a new exception based on the static type of the argument to throw.

    E.g.

    int main()
    {
        try
        {
            try
            {
                throw Derived();
            }
            catch (Base& b)
            {
                std::cout << "Caught a reference to base\n";
                b.print(std::cout);
                throw b;
            }
        }
        catch (Base& b)
        {
            std::cout << "Caught a reference to base\n";
            b.print(std::cout);
        }
    
        return 0;
    }
    

    As written above, the program will output:

    Caught a reference to base
    Derived
    Caught a reference to base
    Base

    If the throw b is replace with a throw, then the outer catch will also catch the originally thrown Derived exception. This still holds if the inner class catches the Base exception by value instead of by reference - although naturally this would mean that the original exception object cannot be modified, so any changes to b would not be reflected in the Derived exception caught by the outer block.

提交回复
热议问题