8
我无法在从void*
投下的对象上调用指向成员函数的指针。见下面的例子:无法通过静态方法调用指向成员函数的指针
class Test
{
public:
Test(int pointTo)
{
if (pointTo == 1)
function = &Test::Function1;
else
function = &Test::Function2;
}
static void CallIt(void* cStyle)
{
Test* t(static_cast<Test*>(cStyle));
(t->*function)();// error C2568: '->*': unable to resolve function overload
}
void CallIt()
{
(this->*function)();// Works just fine
}
private:
typedef void (Test::*ptrToMemberFunc)();
ptrToMemberFunc function;
void Function1()
{
std::cout << "Function 1" << std::endl;
}
void Function2()
{
std::cout << "Function 2" << std::endl;
}
};
int main()
{
Test t1(1);
Test t2(2);
Test::CallIt(static_cast<void*>(&t1));
Test::CallIt(static_cast<void*>(&t2));
t1.CallIt();
t2.CallIt();
return 0;
}
当对象被转换为void*
和后面会发生什么?为什么我不能再调用指向成员函数的指针?
编辑:
修改CallIt()
如下允许程序编译,但我仍然好奇,为什么原来没有工作。
static void CallIt(void* cStyle)
{
Test* t(static_cast<Test*>(cStyle));
Test::ptrToMemberFunc pf(t->function);
(t->*pf)();
}
这很有趣,我只是写完全相同的代码wandbox,下降到identificatiors。 Tuple_cat的回答解释了这一点。基本上你必须链接对象和可调用,所以一个间接运算符是不够的。一些编译器给出了更易于理解的错误消息,就像他们告诉你,你可以这样调用一个静态成员 - 暗示你没有这个指针 – Swift
关于你的编辑,我只是认为运算符' > *'扔掉你。考虑它只是一个名为'call_with_this'的常规函数,它需要一个指向对象和成员函数的指针。那么你最初的不工作呼叫是'call_with_this(t,function);'。这里恰好如此,名称'function'是'Test'类的非静态成员,但它与't'无关。因为你在一个静态函数中,所以没有'this'来查找名字'function'。一旦你要求't-> function',你就有一个具有可访问名称的实际值。 – GManNickG
@GManNickG就是这样。现在我看到了解决方案,我明白了,但我没有意识到' - > *'操作符实际上正在做什么(我正在将它读作'(t - >(* function))')。 – Kerry