2010-05-25 5 views
12

RHEL 5.3을 사용하고 있습니다. gcc 4.1.2와 1.33의 부스트가 있습니다. 부스트 1.33에 빠진 몇 가지 기능이 있습니다. 따라서 새로운 부스트 버전 1.43으로 업그레이드하는 것이 좋습니다.두 버전의 동시 사용하기

  1. 부스터 1.43의 일부 헤더 전용 라이브러리와 나머지 1.33의 헤더를 동시에 사용할 수 있습니까? 예를 들어 boost 1.33에없는 unorded_map을 사용하고 싶습니다.

  2. 서로 다른 릴리스의 바이너리 부스트 라이브러리를 동시에 사용할 수 있습니까? 약간의 운 (및 관리에 많은)와

답변

3

당신이 아마 완전히 새로운 헤더를 사용하여 멀리 얻을 수 있습니다. Boost의 일부분이 다른 부분을 참조하기 때문에 거의 모든 경우에 서둘러 추락 할 수 있습니다. 그리고 어떤 v. 1.33 코드가 실수로 v. 1.43 헤더를 의존성에 대해로드하면 꽤 좋은 기회가 있습니다. 결과적으로 어떤 문제가 생길 수 있습니다 - 당신이 희망 할 수있는 최선책은 그 시점에서 빠르고 깨끗한 죽음 (충돌)이지만 훨씬 더 나 빠지기 쉽습니다 (예 : 침묵하는 데이터 손상).

14

아니요 - 절대하지 마세요!

뜻하지 않은 충돌이 발생할 가능성이 있습니다.

이름 공간 이름 바꾸기를 사용하는 것이 유일한 방법은 부스트 버전을 다른 네임 스페이스에 배치하는 것입니다.

최신 버전의 BCP가이 옵션을 제공합니다. 따라서 boost 대신 boost_1_43과 같은 것을 사용할 것입니다. 그러나 그것은 당신을 위해 아주 투명 할 것입니다. 그러나 당신은 아직도 에 대해 동일한 cpp 파일에서 두 가지 버전의 boost를 사용할 수 없다는 것을 알고 있어야합니다.

또한이 토론에 살펴 : Creating Library with backward compatible ABI that uses Boost

좋아 스크립트, 네임 스페이스의 이름을 변경 정의하고 실제로

#include <boost/foo.hpp> 
#include <myboost/bar.hpp> 

boost::foo f; 
myboost::bar b; 

부스트 BCP이 허용하지 않습니다

같은 부스트 ​​두 버전을 포함 할 수 있도록 포함 .

그러나 일부 라이브러리는 부스트 접두사없이 :: 스레드를 높이고 부스트 : 정규식의 C API를 (regexec는, regcomp에를) 통근 "C"문자 수출로 여전히주의해야합니다

편집

같은 문제의 예를 들어 다음과 같은 파일을 만듭니다

a.cpp :

template<typename Foo> 
Foo add(Foo a, Foo b) 
{ 
     return a+b; 
} 


int foo(int x,int y) 
{ 
     return add(x,y); 
} 

b.cpp :

template<typename Foo> 
Foo add(Foo a, Foo b) 
{ 
     return a-b; 
} 


int bar(int x,int y) 
{ 
     return add(x,y); 
} 

시험.CPP :

30 -10 

하지만 당신은

30 30 

또는

,691를 얻을 수 있습니다 :

g++ a.cpp b.cpp test.cpp 

당신은 기대 :

#include <iostream> 

int foo(int,int); 
int bar(int,int); 

int main() 
{ 
     std::cout<< foo(10,20) <<" " <<bar(10,20) << std::endl; 
} 

을 컴파일

-10 -10 

연결 순서에 따라 다릅니다. 그것은 서로 다른 컴파일 단위에 배치되는 경우

그래서 당신이 실수로 다른 부스트에서 기호를 사용하여이 프로그램 기호 int add<int>(int,int)와 동일한 충돌 할 수있는 두 가지 부스트 버전을 사용하는 동일한 기호에도 에 해결됩니다.

+0

답장의 처음 부분에 동의하지 않더라도 +1 링크입니다. – richj

+0

@richj - 모든 연결이 명시적인 DLL 플랫폼에서는 가능하지만 ELF에 대해서는 나쁜 결과가 발생합니다 (경험에서) – Artyom

1

업데이트

나는 내 원래의 대답은 링커의 기능과 사용되는 옵션에 대한 너무 많은 가정을 생각하고, 그것을 잘 완전히 잘못 될 수있다. 일반적으로 나는 그것을 지울 것이지만, 토론에는 다른 답변에 포함되지 않은 몇 가지 사항이 있습니다.

잘 작동하는 클로즈드 소스 라이브러리를 구축하는 데 의미있는 점이 있습니다.

원래 대답으로 당신이 코드는 컴파일시에 생성되며, 생성 된 심볼은 컴파일 단계의 범위에 국한해야하기 때문에 다음 확인을해야 컴파일 단계 당 하나의 버전을 사용할 때

.

부스트가 여전히 링크 가능한 라이브러리가없는 템플릿 라이브러리라고 가정합니다. 그렇지 않은 경우, 둘 이상의 라이브러리 버전에 링크하지 않는 한 여전히 OK입니다.

내가 잘못 생각할 수도 있지만 그 의미는 응용 프로그램에 정의 된 버전과 다른 버전의 부스트에 대해 빌드 된 타사 라이브러리를 사용할 수 없다는 의미입니다. 읽거나들은 바가 없기 때문에이 제한이 적용된다는 암시를줍니다.

자신 만의 응용 프로그램을 작성하는 경우 자신의 모든 코드에 대해 한 버전의 Boost를 사용합니다. RHEL에서 제공하는 것과 동일한 버전 일 필요는 없습니다.

g++ -c -I/usr/include/boost_1.31 a.cpp 
g++ -c -I/usr/include/boost_1.39 b.cpp 
ar rcs liba.a a.o 
ar rcs libb.a b.o 
g++ -I/usr/include/boost_1.41 test.cpp liba.a libb.a -o test 

... 그것은 여부에 의존하기 때문에 지금은, 툠의 관점을 이해 :

는 업데이트 툠의 예와 비교

, 내가 얘기하고있는 시나리오는 더이 같다 링커는 동일한 라이브러리 파일의 심볼을 선호합니다.

+0

-1 특히 ELF 플랫폼에 대해 이야기 할 때 올바르지 않습니다 – Artyom

+0

ELF가 다음과 같은 의미입니까? /en.wikipedia.org/wiki/Executable_and_Linkable_Format? 그렇다면 그것에 대해 아무 것도 모르지만 C++ 메타 프로그래밍과의 관련성을 알 수는 없습니다. 설명 해주십시오. – richj

+0

@richj 내 대답은 예제를 참조하십시오. – Artyom

관련 문제