2013-03-24 6 views
1

포인터를 int로 변환 한 다음 포인터로 다시 변환하는 간단한 방법이 필요합니다. int는 포인터보다 프로젝트에서 더 쉽게 수행 할 수 있기 때문에 이식성을 위해 int로 필요합니다.포인터를 int로 변환하고 다시 입력 된 객체로

시작 플레이어와 반환 포인터 :

SoundPlayer* player = new FxPlayerTiny(); 
return (int)player; // this works, but is it correct? 

정지 플레이어를 사용하여 포인터 INT :

FxPlayerTiny* player = static_cast<FxPlayerTiny*>((int*)num); // this gives me an error 
FxPlayerTiny* player = (FxPlayerTiny*)((int*)obj); // this works, but is it correct? 
delete player; 
sizeof (int)sizeof (void*)이 다를 수 있습니다, 특히 때문에 위해 (휴대 int를 사용하지 않는 것이 좋습니다
+5

어, int는 어떻게 휴대하기가 더 쉽습니까? 그리고 그 코드는 안전하지 않습니다. – GManNickG

+3

정말 불투명 한 무언가에 캐스트해야한다면, 적어도'void * '를 사용하십시오. – Mat

+0

int가 포인터보다 사용하기가 쉬운 이유는 무엇입니까? 그것은 단지 잘못된 것처럼 들립니다. 또한, 전체 포인터가 int에 들어갈 것이라는 보장은 없습니다. C는 intptr_t (그리고 C++의 대부분의 구현도 제공합니다)를 제공합니다. intptr_t는 포인터를 저장할만큼 충분히 큰 정수 유형입니다. reinterpret_cast를 사용하여 둘 사이를 전환하십시오. –

답변

7

할 일은 포인터를 다룰 수 있도록 프로젝트를 수정하는 것입니다. 정수와 포인터는 다른 두 가지입니다. 앞뒤로 변환 할 수 있지만 조심하지 않으면 이러한 변환으로 인해 정보가 손실 될 수 있습니다.

포인터 값을 int으로 변환하고 다시 실행하면 구현 및 기본 플랫폼에 따라 정보가 쉽게 손실 될 수 있습니다. 예를 들어, int에있는 시스템은 포인터보다 작습니다. int과 64 비트 포인터가 32 비트 인 경우 포인터를 int으로 변환하면 다시 잘못된 포인터가 나타납니다.

long 또는 unsigned long은 정보 손실없이 변환 된 포인터 값을 보유 할만큼 충분히 넓습니다. 나는 그렇지 않은 시스템에서 일한 적이 없다.

SoundPlayer* player = new FxPlayerTiny(); 
return reintrepret_cast<unsigned long>player; 

을 다시 unsigned long 값을 변환 : 예를 들어,

그래서 당신이 쓸 수 (. 하나가 잘 동일하게 작동합니다 개인적으로, 나는하지만 어떤 정말 좋은 이유, 서명되지 않은 유형을 선호하는 경향이있다) reintrepret_cast,SoundPlayer*>을 사용하여 포인터에 연결하십시오.

보다 새로운 구현은 부호없는 정수 및 부호있는 정수 유형 인 타입 정의 uintptr_tintptr_t을 제공하여 정수 - 포인터 변환에 대한 포인터로 올바르게 작동 할 수 있습니다. 그것들은 C99에 소개되었고, 헤더에 정의 된대로으로 정의되었습니다. (포인터가 보다 큰 구현의 경우 정수 유형은 정의하지 않지만 이러한 구현은 드뭅니다.) C++에서는 2011 년 표준을 채택하여 <cstdint> 헤더에 정의했습니다. 그러나 Microsoft Visual C++에서는 2010 버전을 지원합니다.

이 보증은 일반 포인터에만 적용되며 함수 포인터 나 멤버 포인터에는 적용되지 않습니다.

#include <cstdint> 
SoundPlayer* player = new FxPlayerTiny(); 
return reintrepret_cast<std::uintptr_t>player; 

을하지만 먼저,이 고려 :이 작업을 수행해야하는 경우

그래서, 당신은 쓸 수 있습니다.new FxPlayerTiny()은 포인터 값을 제공하며 포인터 값을 원하게됩니다. 가능한 경우 포인터로 유지하십시오. 그것을 정수로 변환한다는 것은 사용할 기술을 결정해야한다는 것을 의미하며 정수 값이 나타내는 포인터 유형을 추적해야합니다. 큰 실수가 아닌 정수형을 사용하거나 저장 한 포인터 유형에 대한 추적을 잃어 버리면 실수로 컴파일러가 실수로 경고합니다.

아마도 포인터를 포인터로 저장할 수 있다면 그럴만 한 이유가있을 것입니다. 그러나 포인터를 포인터로 사용하면 인생이 훨씬 쉬워 질 것입니다.

+0

Microsoft Visual C++는 최소한 2008 년 릴리스부터 'uintptr_t','intptr_t' 및'ptrdiff_t' (항상 잊혀진 파트너)를 지원했습니다. :) –

+0

'ptrdiff_t'는 1989 년 이래로 표준 이었지만,'[u] intptr_t'도 지원한다는 점을 알아두면 좋습니다. –

1

Windows x64 용으로 컴파일 할 때의 예). int가 사용자 인터페이스에 필요하면 포인터 테이블을 사용하고 인덱스를 통해 액세스하는 것이 더 나을 것입니다.

그러나 포인터를 정수로 변환하거나 그 반대로 변환하려는 경우 간단한 변환만으로 충분합니다. 단, sizeof *int) == sizeof (void*) 인 경우는 같습니다.

관련 문제