2014-10-01 2 views
2

나는 C++ 라이브러리에 다음과 같은 구조를 건너 왔어요 :private 멤버 포인터를 NULL과 같은 클래스로 설정합니까?

인 MyClass.cpp에서 MyClass.h

class myClass { 
public: 
static myClass* Instance(); 
. 
. 
private: 
static myClass* _instance; 
. 
. 
}; 

과에

myClass* myClass::_instance = NULL; 

// followed by the all other functions.. 

myClass::myClass() { 
    . 
    . 
} 

myClass* myClass::Instance() { 
    if (_instance == NULL) { 
     . 
     . 
    } 
    . 
    . 
} 

그래서 무엇인가 어떤 함수 밖에서 NULL 포인터가되도록 _instance를 만드는 방법? 그리고이 코드 라인은 언제 실행됩니까?

감사합니다.

편집 : 주 기능 추가. 그리고 포인터의 값을 검사하는 myClass.cpp의 인스턴스 함수. 그래도 포인터가 NULL로 설정되면 이해가되지 않습니다.

int _tmain(int argc, T_CHAR* argv[]) { 

myClass* instance = myClass::Instance(); 

. 
. 
. 

return 0; 
} 
+0

@PaulR 무엇? 그게 어떻게 중복되는거야? 정적 인 멤버에 관한 두 가지 질문이 마술처럼 동일하지는 않기 때문입니다. –

+0

@LightnessRacesinOrbit : 질문의 본질을 완전히 수정 한 후 편집하기 전에 원래 버전의 질문을 확인하십시오. –

+0

@PaulR : 확인한 질문과 중복되는 개정 본이 없습니다. –

답변

1

그렇다면 _instance을 어떤 함수 외부의 NULL 포인터로 사용하는 것은 무엇입니까?

정적 데이터 멤버는 일반적으로 클래스가 포함 된 네임 스페이스에서 하나의 소스 파일에 정의되어야합니다. 그것들은 One Definition Rule의 적용을받으며,이를 사용하는 프로그램에서 정확히 하나의 정의를 가져야합니다. 이것은 그 정의입니다.

NULL으로 초기화하면 처음에 null이되므로 Instance() 함수가 인스턴스가 아직 생성되었는지 여부를 확인할 수 있습니다. 이는 모든 정적 변수와 마찬가지로 명시 적으로 이니셜 라이저를 제공하는지 여부에 상관없이 제로 초기화됩니다.

그리고 언제이 코드 라인이 실행됩니까?

정적 초기화 중 동안 프로그램의 다른 코드보다 앞에; 그것은 일정한 초기화자를 갖는 사소한 형식이기 때문입니다.

0

정적 키워드 란 클래스에서 인스턴스화 할 모든 개체가 공유하고 있음을 의미합니다. 따라서 모든 함수 외부에서 초기화해야합니다. 정적 클래스는 클래스의 모든 인스턴스간에 공유되는 클래스 변수입니다. 이것은 인스턴스 변수의 반대이며, 각 인스턴스는 자체 복사본을 가지고 있습니다. 클래스 변수에 액세스하려면 두 가지 방법이 있습니다. 1) a_class :: static_variable 2) a_class a; a.static_variable. 초기화는 헤더가 아닌 소스 파일 (.cpp)에 있어야합니다. 정적 변수이기 때문에 컴파일러는 하나의 복사본 만 만들어야합니다. 그렇지 않으면 링크 오류가 발생합니다. 헤더에있는 경우 헤더가 포함 된 모든 파일에서 복사본을 얻을 수 있으므로 링커에서 여러 번 정의 된 심볼 오류가 발생합니다.

정적 데이터 멤버는 지정된 클래스 유형의 개체가 아닙니다. 그들은 별도의 객체입니다. 결과적으로 정적 데이터 멤버의 선언은 정의로 간주되지 않습니다. 데이터 멤버는 클래스 범위에서 선언되지만 정의는 파일 범위에서 수행됩니다.

+1

질문에 대답하는 곳이 보이지 않습니다. –

1

나는 한 번 이런 식으로 우연히 만났습니다. 그것은 싱글 톤과 비슷한 것이었다. 첫 번째 getInstance() 함수 호출에서 인스턴스를 초기화하기를 원했던 이유는 _instance 포인터가 처음에 NULL로 초기화되고 (그리고 일부 쓰레기가 아닌) 메모리) 체크 기능이 제대로 작동하는지 확인하십시오.

이 경우는 확실치 않지만 가능한 일입니다.

+0

네, 그렇습니다. 고맙습니다. 생성자 또는 다른 함수의 일부가 아니기 때문에 코드의 특정 줄이 언제 실행되는지 궁금합니다. – simplename

+0

_ "싱글 톤과 비슷한 것이 었습니다."_ 단순히 "유사"하지 않았습니다! –

+0

@pract : 코드에 표시하지 않았습니다. 아마도'myClass'의 일부 정적 멤버 함수에있을 것입니다. –

0
myClass* myClass::_instance = NULL; 

코드는 정적 멤버 변수를 초기화하려고 시도합니다.

0

포인터가 프로그램의 맨 처음부터 NULL 값으로 시작되도록 초기화하는 것입니다. 유용한 포인터 값은 프로그램 중에 나중에 할당하기 전에 그것은 잘못된 포인터를 제공 한

하지만 인식 검증 값. 이렇게하면 포인터가 아직 유용한 값으로 주어 졌는지 여부를 확인하기 위해 포인터를 안전하게 테스트 할 수 있습니다.

이 경우에는 싱글 톤을 표시하기 때문에 표시되지 않은 일부 myClass::getInstancePlease() 기능을 사용하여 "나중에"myClass의 인스턴스를 요청한 경우를 의미합니다.

static 일부 인스턴스 (아마도 동적으로 할당 된 인스턴스)에 대한 포인터가 아닌 static 인스턴스의 함수로 싱글 톤을 구현하는 것이 더 일반적입니다.

정적 저장 기간을 가진 개체로서 어쨌든 그렇게합니다. 그러므로이 초기화는 실제로 프로그래머의 의도를 문서화하는 것 이상의 완전히 무의미합니다.

+0

각주가 잘못되었습니다. 정적 데이터 멤버를 초기화하지 않으면 기본값은 0이 아닙니다.이 멤버는 전혀 존재하지 않으며 액세스하려고하면 링크 타임 오류가 발생합니다. – 5gon12eder

+0

@ 5gon12eder : [그건 완전히 말도 안돼] (http://coliru.stacked-crooked.com/a/6e8db1b25dbbd76c). 너 어디서 들었어?! [당신은 정의를위한 혼동을 혼동하고 있습니다] (http : // coliru.stacked-crooked.com/a/3a384ef6a19548c7). 실제로 모든 정적 스토리지 기간 오브젝트는 프로그램 시작시 첫 번째 단계로 확실히 초기화됩니다. –

+0

맞습니다. "정의하지 않으면 *"라고 말하는 것이 맞을 것입니다. 내가 말하고자하는 것은 코드에서 OP를 혼동하는 선을 제거하면 링커 오류가 발생한다는 것입니다. 따라서 라인은 완전히 무의미하지 않습니다. 'int * Test :: pointer = 0; 대신에'int * Test :: pointer;'를 쓰면 실제로 같은 효과가 나타납니다. – 5gon12eder

관련 문제