C ++ desordenado: argumento opcional obligado a ser obligatorio

Quiero tener una función con argumento opcional. Sin embargo, VC ++ está lanzando un error que no puedo comprender. El código es tan simple como sigue:

#include  #include  #include  using namespace std; void myFunction(string something, int w); int main() { myFunction("a string"); int a = 1; } void myFunction(string something, int w = 5) { cout << something << " - " << w << endl; } 

Se queja:

 'myFunction': function does not take 1 arguments 

Sin embargo, si muevo myFunction () antes de main (), no da ningún error. Que esta pasando? Por favor ayuda. Gracias.

Este error se debe a que tiene variables opcionales cuando llama a su función, pero no en su statement.

Esto creará una función con dos variables:

 void myFunction(string something, int w); 

Sin embargo, esto haría que la segunda variable sea opcional:

 void myFunction(string something, int w=5); 

Necesitas hacer que la statement tenga una variable opcional.

Además, me sorprende que su comstackdor no haya intentado escupir algún tipo de error relacionado con una redefinición. (¡ Eso podría ser incluso un error del comstackdor! Actualizaré la investigación sobre esto. Actualización: No parece un error del comstackdor, pero definitivamente es una característica que me encantaría tener. Incluso si se tratara de un error, estaría relacionado con el enlazador) . )

Alguna terminología: esta

 void myFunction(string something, int w); 

es una declaracion Esta

 void myFunction(string something, int w) { // note the function body } 

Generalmente se le llama definición . Pero en realidad es tanto una definición como una statement . Por simplicidad seguiré llamándolo la definición.

Su problema es que el orden importa, específicamente el orden en el que declara, define y llama a su función. En el sitio de la llamada en main() la única statement visible de myFunction toma una cadena y un entero y no tiene argumentos predeterminados. La definición no es visible en ese momento, por lo que no entra en juego en absoluto. Para el comstackdor parece que intenta llamar a una función que no existe.

Hay dos soluciones:

  1. Mueva el argumento predeterminado de la definición a la statement. Esa es la forma común de hacerlo. En la mayoría de los casos, tiene la statement (incluidos los argumentos predeterminados) en un archivo de encabezado y una definición coincidente (sin los argumentos predeterminados) en un archivo cpp que # incluye el encabezado.
  2. Deshazte de la statement y mueve la definición sobre main() . Esto funciona porque la definición es también una statement.

En este sencillo ejemplo, ambos son igualmente válidos.

Para la definición los argumentos por defecto son irrelevantes. No importa si obtiene el 5 porque alguien lo escribió explícitamente en el sitio de la llamada o si el comstackdor lo agregó a través del argumento predeterminado. Por eso, cuando tiene una statement y definición separadas, el argumento predeterminado solo es necesario para la statement. Puedes y debes dejarlo fuera de la definición. De lo contrario hay que mantenerlo en dos lugares sin ninguna buena razón.