Post

[ STUDY/Effective C++ ] 2022. 6. 23. 20:41

대입(assignment)과 초기화(initialization)를 헷갈리지않기

class People {...};

class Person {
public:
	Person(const std::string& name, const std::int& age);
    
private:
	std::string theName;
	std::string theAge;
};

Person::Person(const std::string& name, const std::int& age)
{
	theName = name;
	theAge = age;
}

위 코드는 초기화가 아니라 대입이다. 

Person::Person(const std::string& name, const std::int& age)
	: theName(name),
	  theAge(age)
{}

위 코드는 대입이 아닌 초기화이다.

앞의 코드는 초기화를 따로하고, 대입을 따로 하기때문에 처음 초기화한 값은 헛것이 되어버린다.

하지만 멤버 초기화 리스트를 이용하면, 복사 생성자를 통해 들어가는 인자가 바로 데이터 멤버에 대한 생성자의 인자로 쓰인다. 이런 면에서 앞의 코드보다 좀 더 효율적이다.

 

Person::Person(const std::string& name, const std::int& age)
	: theName(), //theName의 기본ctor(생성자)호출
	  theAge()
{}

이렇게 매개변수가 있든없든간에 멤버 초기화 리스트에 모두 넣어주는 쪽이 좋다. 

 

비지역 정적 객체의 초기화 순서는 개별 번역 단위에서 정해진다.

정적 객체 : 생성된 시점부터 프로그램이 끝날 때까지 살아 있는 객체 (스택, 힙기반 객체는 애초에 될 수 없음)

                  - 전역 객체

                  - 네임스페이스 유효범위에서 정의된 객체

                  - 클래스 안에서 static으로 선언된 객체

                  - 함수 안에서 static으로 선언된 객체

                  - 파일 유효범위에서 static으로 정의된 객체

 

함수 안에 있는 개체 -> 지역 정적 객체 (함수라는 지역성을 가짐)

나머지 -> 비지역 정적 객체

 

별개의 번역 단위에서 정의된 비지역 정적 객체들의 초기화 순서는 정해져있지않다.

이러한 사실로 인해 초기화되지도 않은 객체를 사용할 일이 생길수도 있다는것이다.

 

이는 비지역 정적 객체를 지역 정적 개체로 바꾸면 해결되는 일이다.< 단일체 패턴 >

비지역 정적 객체를 하나씩 맡는 함수를 준비 - 안에 객체를 넣음 - 함수에서는 그 객체에 대한 참조자를 반환하게함.

=> 사용자가 직접 비지역 정적 객체를 참조x , 함수호출로 대신함! 

▲ top