gpt4 book ai didi

c++ - 对象方法的真实地址

转载 作者:太空狗 更新时间:2023-10-29 21:06:12 24 4
gpt4 key购买 nike

我知道我可以创建方法指针,而且我知道它们通常不同于函数指针。不允许在它们之间进行转换。方法指针可以包含大量有关如何调整 this 指针等的数据。

我想知道如何获取正在执行给定方法的代码的实际地址。该地址不会以任何方式被引用,但将用作给定方法所属类型的标识符 - 有点像 RTTI,具有对库边界不敏感的优点,因为此代码通常仅在一个单元中可用.

编辑:

为什么我不添加一些返回对象类型的 getType() 方法?

因为我不仅希望能够以这种方式使用我创建的类。我想做的基本上是我对 variant 类的实现,它基本上可以接受所有内容,前提是存在针对给定类型的 void* getVariantId() 的专门化。

然后我可以写:

template <typename T>
class getTypeId{
};

class foo{
public:
void bar();
};

// getTypeId declared but not defined for generic type T earlier...
template <>
class getTypeId<foo>{
static void* get<foo>(){
return &foo::bar;
}
};

void doSomething(myVariant var);

int main(int argc, char* argv[]){
foo f;
myVariant var = myVariant::fromType<foo*>(&f);
doSomething(f);
}

void doSomething(myVariant var){
foo* f = var.toType<foo*>(); // Returns foo object from main
int* i = var.toType<int*>(); // returns null, as var is not int* in my example.
}

fromType 的想法是使用getTypeId 获取类型的表示值,并将其与转换为void* 的对象指针一起strongig。另一方面,toType 比较从 `getTypeId::get 获取的值和存储在对象中的值 - 如果匹配,则将内部保存的对象指针重新解释回原始类型并返回。

这个解决方案的美妙之处在于,即使有一些共享库 X 定义了类型 x,然后是库 Y 和 Z,它们分别使用库 X 也会同意类型 x 是相同的(例如,如果变体创建在 Y 中传递给 Z),因为 X::method 上的地址保持不变。作为 Y 或 Z 库(但不是 X!!!)的创建者,我不需要确保 X 库启用了 RTTI,甚至不需要知道 myVariant 的存在,但类型 x 仍然完全兼容 myVariant。

编辑2:

我现在看到没有独立于实现的方法来完成这项工作。但是我认为这是不常需要的怪癖,因此不存在的功能,而不是无法创建的功能。我想我还没有说清楚我想要实现什么以及我是如何计划这样做的。所以:

  • 这里所说的库是指共享库(.dll、.so 等)。

  • 每个非纯虚拟的方法(意味着每个已定义的方法)都必须有实现。此实现表现为接受一个附加参数 this 的函数 - 虚函数仅在调用方有所不同。让我们以类 X 及其方法 X::foo 为例。这个方法只绑定(bind)到X类型,即使Y类型继承它,这个方法仍然是X::foo,因此它足以识别类型X。覆盖子类 Xchild 中的虚方法或覆盖方法实际上是用新地址定义新方法 Xchild::foo。那么您可能会使用 Xchild::foo 来表示 Xchild,而不是 X

  • 如果类型 X(准确地说是它的所有方法)在库 libX 中定义,并且 libY 和 libZ 都在使用 libX(但彼此不认识),并使用第一种方法为它们自己的目的定义 getTypeId在 X 中表示它(请注意,这不会对 libX 开发人员施加任何影响),然后他们就 X 是什么类型达成一致。如果应用程序开发人员使用 libY 获取变体并将其传递给 libZ,两者都会正确识别提到的类型。

  • 我不是在尝试开发类型转换变体 - 保存为 X 的变体只能作为 X 读取,即使传递给 myVariant 的实际指针是 Xchild。我对获取给定实例的最顶层类的类型不感兴趣 - 只是用于创建变体的类。

最佳答案

C++ FAQ Lite 将整个部分用于 Pointers to Member Functions .

有两个答案特别说明了为什么您尝试做的事情无法完成(至少不能以可移植的方式):

  • 指向成员函数的指针是一种不同的动物:

C++ introduces a new type of pointer, called a pointer-to-member, which can be invoked only by providing an object. Do not attempt to "cast" a pointer-to-member-function into a pointer-to-function; the result is undefined and probably disastrous. E.g., a pointer-to-member-function is not required to contain the machine address of the appropriate function.

  • 指向成员函数的指针可以指向虚函数:

A pointer to a member function might be a data structure rather than a single pointer. Think about it: if it's pointing at a virtual function, it might not actually be pointing at a statically resolvable pile of code, so it might not even be a normal address.

关于c++ - 对象方法的真实地址,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8042256/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com