2010-03-09 10 views
7

¿Por qué aparece un error de discard qualifiers:g ++: const descarta calificadores

customExc.cpp: In member function ‘virtual const char* CustomException::what() const’: 
customExc.cpp: error: passing ‘const CustomException’ as ‘this’ argument of ‘char customException::code()’ discards qualifiers 

en el siguiente ejemplo de código

#include <iostream> 


class CustomException: public std::exception { 

public: 

    virtual const char* what() const throw() { 
     static std::string msg; 
     msg = "Error: "; 
     msg += code(); // <---------- this is the line with the compile error 
     return msg.c_str(); 
    } 

    char code() { return 'F'; } 
}; 

He buscado en todo el SOF antes con respecto a cuestiones de simular.

Ya he agregado un const en cada lugar posible.

favor ilumíneme - No entiendo el punto ...

EDITAR: Estos son los pasos para reproducir en Ubuntu-carmic-32 bits (g ++ v4.4.1)

  1. guardar ejemplo como customExc.cpp
  2. tipo make customExc.o

EDITAR: El error está relacionado con CustomException. La clase Foo no tiene nada que ver con eso. Así que lo he borrado.

+2

Por cierto, no debe devolver 'msg.c_str()', ya que 'msg' se destruye tan pronto como' what() 'regrese, lo que significa que el puntero ya no será válido cuando el usuario lo lea . Es posible que desee considerar construirlo en el momento de la construcción y almacenarlo como miembro de la clase. –

+0

@Raphael: Lo sé. Solo quería mantener el ejemplo lo más simple posible.Y, dado que el valor de retorno de 'what()' es 'const', no debería ser un problema en la práctica. –

+1

No veo qué tiene que ver el valor de retorno de 'what()' con 'const' con la seguridad de devolver' msg.c_str() '... se garantiza que apunta a la memoria inexistente, que es comportamiento indefinido no hagas eso! – rmeador

Respuesta

14

CustomException::what llamadas CustomException::code. CustomException::what es un método const, como lo indica la const después dewhat(). Como es un método const, no puede hacer nada que pueda modificarse a sí mismo. CustomException::code no es un método const, lo que significa que no promete no modificarse. Entonces CustomException::what no puede llamar al CustomException::code.

Tenga en cuenta que los métodos const no están necesariamente relacionados con las instancias const. Foo::bar puede declarar su variable exc como métodos no const y call const como CustomException::what; esto simplemente significa que CustomException::what se compromete a no modificar exc, pero puede que otro código lo haga.

Las preguntas frecuentes de C++ tienen un poco más de información en const methods.

+0

@Josh: Ahora lo tengo, y finalmente acepté tu respuesta debido a' 'what() promete no modificar exc ...' –

3

Su what() es una función de miembro constante, pero code() no lo es.

Simplemente cambie code() por code() const.

4
int code() const { return 42; } 
+1

Gracias, esto me ayudó. Estaba poniendo const antes del nombre de la función no después. –

3

Su función miembro code() no se declara const. Llamar a funciones miembro no constantes de las funciones miembro miembro (what() en este caso) es ilegal.

Haga su code() miembro const.

+1

que es un mensaje de error bastante opaco ... – rmeador

+0

@meador: A ** const ** en un método significa que ** this ** será un puntero-a-const en este método. Si es consciente de eso, el mensaje de error tiene mucho sentido: cuando intenta llamar 'code()' desde 'what()', está tratando de convertir '(const CustomException *) this' into' (CustomException *) this', descartando de este modo el/los calificador (es) de cv (** const **) – UncleBens

+0

Creo que @rmeador hace un buen punto. Estoy acostumbrado a ese mensaje de error, pero podría decir lo mismo "No puedo llamar a 'char customException :: code()' de 'virtual const char * CustomException :: what() const' porque 'char customException :: code() 'no es una función de miembro constante. " – Ben

Cuestiones relacionadas