Vraag Zijn alle functies "niet-uitzondering" als uitzonderingen zijn uitgeschakeld?


Als u uitzonderingen uitschakelt door compileren met -fno-exceptions zijn alle functies die als niet-uitzondering worden beschouwd, bijvoorbeeld door std::move_if_noexcept of moet je om die reden nog steeds geen functies declareren?


22
2018-02-06 08:13


oorsprong


antwoorden:


De -fno-exceptions zal voorkomen dat je uitzonderingen gooit, maar het kan niet voorkomen dat uitzonderingen uit bibliotheken worden gegooid.

Het volgende voorbeeld wordt bijvoorbeeld beëindigd vanwege een niet-toegestane uitzondering:

#include <vector>

int main()
{
    std::vector<int> v{1,2,3,4,5,6};

    return v.at(55);
}

Maar het volgende voorbeeld zal niet compileren, vanwege -fno-exceptions keuze :

int main()
{
    throw 22;
}

Het mislukt met:

g++   -std=c++11 -g  -Wall -Wextra -fno-exceptions ./garbage.cpp 
./garbage.cpp: In function ‘int main()’:
./garbage.cpp:4:8: error: exception handling disabled, use -fexceptions to enable
  throw 22;

Van dit artikel, Doen zonder hoofdstuk :

Gebruikerscode die C ++ -woorden gebruikt zoals gooien, proberen en vangen   fouten veroorzaken, zelfs als de gebruikerscode libstdc ++ headers heeft opgenomen   en gebruikt constructies zoals basic_iostream.


Aan de andere kant, noexcept markeert de methode als een methode die geen uitzonderingen genereert. Elke gegooide uitzondering zal bellen std::terminate (zie [except.terminate] / 2 in c ++ standaard).

Volgend voorbeeld:

struct A
{
    void foo() noexcept
    {
        throw 33;
    }
};

int main()
{
    A a;
    try
    {
        a.foo();
    }
    catch(...)
    {
    }
}

eindigt met:

terminate called after throwing an instance of 'int'
Aborted (core dumped)

Tot slot: het gedrag is heel anders wanneer je gebruikt -fno-exceptions en wanneer u de functie markeert als noexcept.


Hoewel ik mijn hele project compileer met -fno-exceptions (om andere redenen), moet ik nog steeds bewegingsconstructors verklaren om een ​​move-opdrachtoperator te gebruiken, behalve om semantisch verkeer in te schakelen voor std: move_if_noexcept?

Wanneer u die optie gebruikt, worden de functies niet automatisch gemarkeerd als geen uitzondering. Je moet het handmatig doen. Het is de compiler niet toegestaan ​​om dergelijke wijzigingen aan te brengen.

Als een dergelijke wijziging is toegestaan, dan dit voorbeeld zou verschillende outputs produceren.


20
2018-02-06 10:07