2012-07-11 2 views
2

내 정적 라이브러리와이를 사용하는 프로젝트 각각에 대해 모듈 이름을 어떻게 든 정의해야합니다. 단순히 정적 멤버 초기화 중에이 값이 필요하므로정적 라이브러리의 인라인 함수는 사용자 프로젝트에서 같은 이름의 함수로 대체됩니다.

std::string const module_name = "my module"; 

으로 처리 할 수 ​​없습니다. 정적 데이터 초기화 순서가 정의되어 있지 않으므로 변수을 사용하려고 시도하는 동안 변수를 초기화 할 수 없습니다. 이 문제를 해결하려면

나는 각 모듈에 대해

inline std::string const& module_name() 
{ 
    static std::string const name = "my module"; 
    return name; 
} 

을 정의했다. 그러나 모든 module_name() 호출이 부모 모듈에서 구현을 사용하도록 해결 되었기 때문에 (module_name()은 항상 상위 실행 파일 프로젝트의 이름을 반환합니다)이 방법은 효과가 없습니다. 그리고 나는 왜 그런지 이해하지 못합니다. 이 인라인 함수는 정적 라이브러리에서 정의되고 사용되기 때문에 실제 모듈 이름을 캡처해야합니다. 이 함수가 컴파일러에 의해 인라인되지 않았기 때문입니까?

이 문제를 해결하기위한 권장 방법이 있습니까?

컴파일러 : 외부 링크와 VC++ 10

+1

어때요 ... 네임 스페이스입니까? – Xeo

+0

@Xeo : 명시 적으로'particular_ns :: module_name()'을 백 개 장소에서 지정할 필요가 없습니까? 또한 실수를 저지르는 것이 가능합니다. 복사/붙여 넣기. –

+2

'module_name'을 from에서 호출하는 것이 아니라면, 특정 네임 스페이스에도 있어야합니다. – Xeo

답변

2

엔티티 테스트 VC++ (10)와 GCC는, 단지 프로그램의 하나의 정의를 가질 수 있습니다, 그래서 당신은 여러 정의를 가질 수 없습니다 놀라운 일이 아니다 하나의 프로그램에서 동일한 기능.

인라인과 관련이없는 링커는 동일한 심볼 (템플릿 인스턴스화 및 인라인 함수와 함께 자주 발생하는)과 동적 기호를 사용할 때 다른 심볼의 여러 정의를보고 사용하는 정의 하나를 선택합니다.

각 라이브러리를 별도의 정의로 만들려면 함수를 정적으로 만들거나 이름없는 네임 스페이스에 넣거나, __dllimport 또는 __attribute((visibility("hidden")))과 같은 플랫폼 별 메서드를 사용하여 내부 연결을 수행해야합니다. 컴파일러는 심볼을 공유 라이브러리에 전용이므로 익스포트하지 않아야하므로 동일한 심볼의 다른 정의로 ​​대체되지 않습니다.

또는 각 모듈을 자체 네임 스페이스에 넣고 함수 그 네임 스페이스에서 각 함수는 다르며 간섭하지 않습니다.

+0

+1 : 이름없는 네임 스페이스가 뛰어납니다. –