2016-09-22 4 views
2

Nous voudrions avoir une propre définition de std::runtime_error:runtime_error(const string& arg). Nous mettons en œuvre ce constructeur en termes de l'autre constructeur, à savoir, std::runtime_error:runtime_error(const char*), comme:gcc 4.9.1 n'est pas conforme aux normes? (std :: runtime_error)

namespace std { 
    runtime_error::runtime_error(const string& arg) 
    : runtime_error(arg.c_str()) { 
    ... 
    } 
} 

Avec gcc-4.9.1, cela est impossible, puisque le constructeur std::runtime_error::runtime_error(const string& arg) n'existe pas. Dans gcc/4.9.1/include/C++/4.9.1/stdexcept, nous voyons ce qui suit:

... 
class runtime_error : public exception 
{ 
    string _M_msg; 
    public: 
    /** Takes a character string describing the error. */ 
    explicit 
    runtime_error(const string& __arg); 
    virtual ~runtime_error() _GLIBCXX_USE_NOEXCEPT; 
    /** Returns a C-style character string describing the general cause of 
    * the current error (the same string passed to the ctor). */ 
    virtual const char* 
    what() const _GLIBCXX_USE_NOEXCEPT; 
}; 
... 

La norme indique clairement qu'il devrait y avoir un constructeur runtime_error(const char*) explicite.

19.2.6 Classe runtime_error [runtime.error]

namespace std { 
class runtime_error : public exception { 
public: 
explicit runtime_error(const string& what_arg); 
explicit runtime_error(const char* what_arg); 
}; 
+5

"* Nous implémentons un tel constructeur en termes de l'autre constructeur *" Pourquoi voudriez-vous? Celui qui prend un 'std :: string' a une longueur intégrée, alors que l'autre doit faire un' strlen' pour calculer la longueur. C'est juste une perte de temps inutile. En outre, vous n'êtes pas autorisé à réécrire des classes dans la bibliothèque standard. –

+0

Utilisez-vous '-std = C++ 11'? –

+0

@FredLarson Devrait être la valeur par défaut. –

Répondre

1

Peut-être que cela ne répond pas à votre question initiale, mais si l'intention est vraiment intercepter le runtime_error instanciation, vous pouvez faire comme ça (gcc Asuming est utilisé):

namespace std { 
    runtime_error::runtime_error(const string& arg) 
    #if (__GNUC__ > 4) 
    : runtime_error(arg.c_str()) 
    #else 
    : _M_msg(arg) 
    #endif 
    { 
    // intercept here! 
    } 
} 

Si tout va bien, le invoqué runtime_error(const char*) ne sera pas mis en œuvre à l'avenir en termes de runtime_error(const string&), qui briserait tout votre espoir et le désir. =)