2013-09-25 5 views
4

전달 선언에 대한 많은 기사를 읽었지만 여전히 질문이 있습니다.C++ 전달 선언 및 파일 디자인

// File a.hpp (in this question I avoid writing guards in header files, for the sake of simplicity) 

class A 
{ 
    // Class B is used only by pointer, the compiler doesn't need to know the structure 
    // of the class, so a forward declaration is enough 
    public: 
     A(void); 
     void Method1(B *pB); 
     void Method2(B *pB);   
}; 

// File a.cpp 

#include "a.hpp" 

A::A(void) { } 

// Some methods of class B are used, so the compiler needs to know the declaration of the class, it cannot be forward declared 

void A::Method1(B *pB) 
{ 
    // Something... 
    pB->SomeMethod(); 
    // Something ... 
} 

void A::Method2(B *pB) 
{ 
    int var = pB->GetSomeMember(); 
    // Something ... 
} 

좋아, 지금의 한 헤더 클래스 B 선언에 대한 파일 및 전방 선언에 대한 또 다른 하나를 가지고 가정하자 : 의 우리가 있다고 가정하자

// File b.hpp 

// Class declaration 
class B 
{ 
/* ... */ 
}; 

// File b_fwd.hpp 

// Forward declaration 
class B; 

내가에 내놓고, 염두에두고 이전 고려 사항은 a.hpp (클래스 B의 전달 선언 만 필요함)에 "b_fwd.hpp"를 포함하고 a.cpp 파일 (선언이 필요한)에 "b.hpp"를 포함하는 것입니다. 다음과 같이 :

// File a.hpp 

#include "b_fwd.hpp" // Forward declaration of class B 

class A 
{ 
    public: 
     A(void); 
     void Method1(B *pB); 
     void Method2(B *pB);   
}; 

// File a.cpp 

#include "a.hpp" 
#include "b.hpp" // Declaration of class B 

A::A(void) { } 

void A::Method1(B *pB) { /* like before ... */ } 

void A::Method2(B *pB) { /* like before ... */ } 

나는이 작품을 알고 있지만 클래스 A에서 나는 두 번 "클래스 B"를 처음으로 선언하고 두 번째로 "정상적으로"포함 시켰기 때문에 이것은 약간 이상하게 들린다. 나는 이것이 좋은 관행인지 그리고 그것이 프로젝트에서 수행 될 수 있는지 없는지 알고 싶다.

+2

단순히'a.hpp'에'class B'를 선언하지 않으시겠습니까? 별도의 헤더에 넣으면 어떻게 될 것으로 생각하십니까? '#include "some_file"지시어는 기본적으로 전처리 기가 컴파일 단계 이전에 지시어가있는 파일에서'some_file'의 내용을 복사하도록합니다. – JBL

+1

알아,하지만 .hpp 파일에 "캡슐화"하는 것을 선호한다. 예를 들어, 네임 스페이스 또는 템플릿이있는 경우 오류가 발생할 위험이 있고 나중에 변경해야 할 문제가있을 때마다 작성하고 싶지는 않지만 .hpp 파일에서 한 번만 wirte합니다. – yuko

답변

4

나는이 기술을 종종 아주 성공적으로 사용한다.

"왜 그냥 앞으로 선언하지 않을까요?"라는 질문에 대답하십시오. 때로는 신고하기가 어렵습니다. 예를 들어 클래스가 템플릿 클래스 인 경우 전달 선언에 템플릿 매개 변수와 클래스 이름이 포함되어야합니다.

+0

흠, 이것이 유용하다고 생각하지 않습니다! 나는 JBL의 제안을 따를 것이다. 최소한 사용자가 클래스를 사용해야 할 때 그는 제공된 모든 템플릿 매개 변수에 익숙해야하며 적절한 순방향 클래스 선언을 작성할 수 있어야합니다. –

+2

당신이 그것을 사용할 계획이라면, 당신이 세부 사항을 알아야한다. 당신은 그 클래스에 대한 메인 헤더 파일을 포함시킴으로써 그것들을 얻는다. 참조 또는 포인터를 매개 변수로 전달하려는 경우 많은 다른 헤더 파일에서 템플릿 매개 변수를 복제하면 유지 관리가 어려워집니다. –

+0

_'Maintenance'_ 그건 논쟁 거리예요! –