2012-02-26 1 views
11

Duplicar posible:
Why is it an error to use an empty set of brackets to call a constructor with no arguments?¿Por qué no se llama al constructor cuando() se usa para declarar un objeto?

$ cat cons.cpp 
#include <iostream> 

class Matrix { 
private: 
    int m_count; 

public: 
    Matrix() { 
     m_count = 1; 
     std::cout << "yahoo!" << std::endl; 
    } 
}; 

int main() { 
    std::cout << "before" << std::endl; 
    Matrix m1();       // <---- 
    std::cout << "after" << std::endl; 
} 
$ g++ cons.cpp 
$ ./a.out 
before 
after 
$ 

¿Qué la sintaxis Matrix m1(); hacer?

Creo que es lo mismo que Matrix m1;. Obviamente estoy equivocado.

Respuesta

12
Matrix m1(); // m1 is a function whose return type is Matrix. 

También esta entrada de lite de C++ FAQ debería ser útil.

Is there any difference between List x; and List x();

+1

@Lazer: convencer a sí mismo, trate de usar m1 (por ejemplo, acceso a m1.m_count) ... – Francesco

+0

En C++ 11 se puede utilizar llaves para todas las llamadas de constructor esto evita el análisis más molesto de C++, es decir, Matrix m1 {}; – mark

+0

Este no es el "análisis más irritante", el análisis más irritante es cuando intentas declarar, objetar y pasar un valor inicializado temporalmente a uno o más de sus parámetros de constructor. P.ej. 'A b (A());'. 'Matrix m1();' es solo una declaración de función normal. –

3

Matrix m1() declara una función que no toma parámetros y devuelve un Matrix. Se puede ver esto es por lo que mediante la adición de un método para Matrix y tratando de invocar en m1:

#include <iostream> 

class Matrix { 
private: 
    int m_count; 

public: 
    Matrix() { 
     m_count = 1; 
     std::cout << "yahoo!" << std::endl; 
    } 
    void foo() {} 
}; 

int main() { 
    std::cout << "before" << std::endl; 
    Matrix m1(); 
    m1.foo(); 
    std::cout << "after" << std::endl; 
} 

da error: request for member 'foo' in 'm1', which is of non-class type 'Matrix()'

0

Esto va a hacer lo que estamos tratando de hacer:

int main() { 
    std::cout << "before" << std::endl; 
    Matrix m1;       // <---- 
    std::cout << "after" << std::endl; 
} 

En C++, si inicializa una variable con parens, en realidad declara una función que no toma parámetros y devuelve ese tipo.

1

pensar desde el punto de vista del lenguaje C:

int data_member(); 

es en realidad un prototipo para la función de tomar nulo y un entero de retorno. Cuando se cambia se siente:

T data(); 

todavía es una declaración de función, resintonizar T. Cuando tiene que declarar como variables, que hace:

T data; // int data; 
Cuestiones relacionadas