2014-12-23 19 views
11

Ho incontrato questa domanda C++:Perché "Fo f (Bar());" può essere una dichiarazione di una funzione che prende tipo Bar e restituisce tipo Foo?

Domanda: la seguente è una definizione o una dichiarazione?

Foo f(Bar()); 

Risposta: E 'forse sia una dichiarazione di una funzione che prende tipo bar e ritorna tipo Foo o è una definizione di f come un tipo Foo, che ha un costruttore che accetta di tipo bar. Il problema è che la sintassi per entrambi è identica, quindi per risolvere questo problema lo standard C++ afferma che un compilatore deve preferire le dichiarazioni di funzioni alle definizioni oggetto dove non è in grado di fare una distinzione.

- Non capisco perché possa essere "una dichiarazione di una funzione che accetta tipo Bar e restituisce tipo Foo"? come mai una parentesi "()" appare nella lista dei parametri?

+1

JFC non questa roba di nuovo –

risposta

11

La funzione f utilizza effettivamente un puntatore a funzione per una funzione che non accetta argomenti e fornisce un valore Bar. Il tipo dell'argomento su f è Bar (*)().

Questo codice non riesce a compilare (e possiamo vedere il tipo effettivo dell'argomento nel messaggio di errore):

class Foo { }; 
class Bar { }; 

Foo f(Bar()); 

int main() { 
    Bar b; 
    f(b); 
    return 0; 
} 

Ma questo codice si compila:

class Foo { }; 
class Bar { }; 

Foo f(Bar()); 

Bar g(); 

int main() { 
    f(g); 
    return 0; 
} 

La seconda significa che potrebbe avere, come dici tu nella domanda, che stai creando un nuovo oggetto chiamato f e stai chiamando il costruttore con Bar() (una nuova istanza di Bar). Sarebbe simile a:

Foo f = Foo(Bar()); 

In questa situazione di Foo f(Bar()); però, la prima interpretazione è scelto dal compilatore.

Un po 'confusamente, se si aggiunge un altro insieme di parentesi, come in

Foo f((Bar())); 

il compilatore sceglie la seconda interpretazione.

+0

perché il primo pezzo di codice non viene compilato? non è la seconda possibilità menzionata nel post originale, una definizione di f come un tipo Foo, che ha un costruttore che accetta il tipo Bar? – athos

+0

@athos perché 'f' si aspetta un puntatore a funzione come primo argomento. L'istruzione 'f (b);', 'b' non è un puntatore func in questo contesto. – greatwolf

+0

@greatwolf vedo. questo compilatore preferisce le dichiarazioni di funzioni alle definizioni dell'oggetto. – athos

Problemi correlati