2012-10-24 2 views
2

다음 코드 스 니펫을 사용하여 C++에서 객체를 만드는 두 가지 방법을 비교합니다. 이 코드에서객체 생성과 관련된 생성자 및 소멸자 호출

#include <iostream> 

using std::cout; 
using std::endl; 

class Foo { 
    public: 
     Foo() : x(0) { cout << "In Foo constructor." << endl; } 
     ~Foo() { cout << "In Foo destructor." << endl; } 
     Foo(const Foo&) { cout << "In Foo copy constructor." << endl; } 

     // Assignment operator. 
     Foo& operator=(const Foo&) { 
      cout << "In assignment operator." << endl; 
      return *this; 
     } 

    private: 
     int x; 
}; 

int main() { 

    cout << "Constructing Foo 1" << endl; 
    Foo Foo_1; 
    cout << "Constructing Foo 2" << endl; 
    Foo Foo_2 = Foo(); 

    return 0; 
} 

출력은 : 나는 비주얼 C++ 2010 (컴파일러 버전 16.x)를 사용하고 내가 cl /EHsc /W4 test.cpp를 사용하여 조각을 컴파일하고

Constructing Foo 1 
    In Foo constructor. 
    Constructing Foo 2 
    In Foo constructor. 
    In Foo destructor. 
    In Foo destructor. 

. Foo_2을 만들 때 임시 객체를 할당하기 위해 생성자와 소멸자를 추가로 호출하고 할당 연산자를 호출하여 임시 객체를 Foo_2에 할당하려고합니다. 누군가 이것이 왜 그런지 설명 할 수 있습니까? 내가 여기서 아주 명백한 것을 놓치고 있다면 사과드립니다.

답변

1

Foo Foo_2 = Foo();Foo Foo_2(Foo());과 유사합니다. 컴파일러는 이것을하기에 충분히 똑똑하기 때문에 대입 연산자가 호출되지 않습니다. BTW, 할당 연산자에 버그가 있습니다. 오브젝트를 복사하는 대신 오브젝트에 대한 참조를 반환합니다. 직접

Foo f1; 
Foo f2 = Foo(); 

첫 번째 구조 f, 기본 생성자를 사용 :

+3

아니, 구문 설탕 아니에요. 'Foo'의 복사 생성자를 private로 만들고 다시 시도하십시오. –

+0

@Pete Becker - 내 잘못, 답장을 수정했습니다 – SomeWittyUsername

+0

'Foo Foo_2 (Foo()); '는 왜 그의 샘플에 단지 두 개의 생성자가 3 개가 아닌지 설명하지 않습니다. –

4

Foo 사용할 수 초기화의 두 가지 형태가있다. 두 번째는 기본 생성자를 사용하여 임시 유형 Foo을 생성하고 임시로 f2에 복사합니다. 후자는 예상 한대로 묘사합니다. 그리고 하나의 추가 규칙을 제외하고는 올바른 것입니다. 초기화 형식이 유효하면 (여기에 복사 생성자를 비공개로 만들고 어떤 일이 발생하는지) 컴파일러에서 복사 구성을 "삭제"하고 f2을 생성 할 수 있습니다 직접, 첫 번째 버전에서와 마찬가지로. 그것이 당신이보고있는 것입니다. 컴파일러는 복사 생성자를 삭제할 필요가 없지만 최근에 사용한 모든 복사본 생성자가 사용합니다.

+0

안녕 피트, 감사합니다. 이것은 나를 위해 그것을 설명합니다. – Francis

+0

Hi Pete, 복사 생성자를 비공개로 설정하고 코드가 컴파일되지 않는 테스트를 시도했습니다. 그것은 개인 회원 Foo :: Foo에 액세스 할 수 없다는 내용입니다. 내 질문은 지금 그것이 복사를 만드는 경우 그 이유는 "Foo 복사 생성자에서 볼 수 없습니다." 출력에. – Francis

+0

안녕하세요, 사과, 나는 Sapien2의 게시물에있는 링크에서 왜 내가 그것을 보지 않을 것이라고 생각합니다. 컴파일러는이를 최적화합니다. 링크에서 인용 : "컴파일러는 실제로 이런 종류의 상황에서 복사 구성을 최적화하는 것이 허용되지만 (필수는 아님) 최적화를 수행하면 복사기에 계속 액세스 할 수 있어야합니다." 너는 이것도 위에 말한다. – Francis

1

문제의 첫 번째 "전문가"http://www.gotw.ca/gotw/001.htm 특히 컴파일러 최적화 노트.

+0

링크를 제공해 주셔서 감사합니다. 또한 도움이됩니다. 나는 묻기 전에 더 많은 인터넷 검색을 했어야했다! – Francis

관련 문제