正如标题所说,我现在正在做一些带有C ++指针的小黑客,但是有些东西在这里没有用到我得到的东西:
uintptr_t texture_pointer = (int)((void*) &texture);
纹理是一个类;这似乎工作正常,因为我得到一个指针值,我已经保证我得到了相同的值到我的其他函数,这应该得到对象;这是失败的代码:
std::cout << "C++ BEFORE: " << texture_pointer << std::endl;
Texture texture = *(Texture*)((void*) texture_pointer);
std::cout << "C++ AFTER: " << (uintptr_t)((void*) &texture) << std::endl;
我的输出除外;是两个相同的数字,但是我得到两个不同的数字,因此为什么我认为必定有错误,但我似乎无法找到它。
示例输出:
C++ BEFORE: 2685236
C++ AFTER: 2684960
答案 0 :(得分:9)
这一行:
Texture texture = *(Texture*)((void*) texture_pointer);
创建新 Texture
对象作为原始对象的副本。显然,这与旧的地址不同。
你可以这样做:
Texture &texture = *(Texture*)((void*) texture_pointer);
(即创建对旧旧的引用)。
但总的来说,弄乱像这样的指针比它的价值更麻烦。
答案 1 :(得分:4)
要与void指针进行强制转换,请使用static_cast
。要使用整数进行强制转换,请使用reinterpret_cast
:
SomeType* p;
// Make sure the type can hold a pointer.
std::uint64_t i = reinterpret_cast<std::uint64_t>(p);
...
SomeType* q = reinterpret_cast<SomeType*>(i); // Guaranteed to yield p back
答案 2 :(得分:1)
除了在其他答案中已经指出的错误之外,这一行不正确,并且可能在64位系统(LP64)上失败:
uintptr_t texture_pointer = (int)((void*) &texture);
应该是:
uintptr_t texture_pointer = (uintptr_t)&texture;
(假设您出于某种原因想要使用C风格的强制转换而不是正确的C ++强制转换)。
答案 3 :(得分:0)
最初,您获取在堆栈上分配的对象的地址,而不是在堆上。这一行:
Texture texture = *(Texture*)((void*) texture_pointer);
然后将该对象复制到堆栈上分配的另一个对象。然后你取第二个地址的地址。
当您处理两个不同的对象时,您有两个不同的地址。
答案 4 :(得分:0)
如果我在这行中正确计算了'*'
Texture texture = *(Texture*)((void*) texture_pointer);
创建一个whatevery texture_pointer指向的副本。
所以,texture和* texture_pointer是不同的存储位置,这就是为什么&amp; texture和texture_pointer有不同的值。
答案 5 :(得分:0)
Texture texture = *(Texture*)((void*) texture_pointer);
此行创建一个新对象,并将texture_pointer指向的对象分配给它。这与创建指针并使其指向对象不同。当您将一个对象分配给另一个对象时,您基本上将旧对象的内容复制到新对象中。那么,有意义的是,两个打印的地址是不同的 - 它们是两个不同对象的地址。