如何调用成员函数指针?

Posted

技术标签:

【中文标题】如何调用成员函数指针?【英文标题】:How do I call a member function pointer? 【发布时间】:2014-06-20 10:52:10 【问题描述】:

我在 Ubuntu 12.04 LTS 32 位上使用 C++11 和 GNU 工具链。我知道有人问过类似的问题,但我还没有完全找到这个问题,而且我无法从已经发布的内容中得到任何有用的东西,所以这里是:

我有这样的代码:

enum class FUNC_TYPES  FUNCTYPE_1,FUNCTYPE_2,FUNCTYPE_3;

class AClass

...

typedef void (AClass::* TFunc )( );
std::map<FUNC_TYPES, TFunc> mFuncMap;


void doStuff();

....


我像这样初始化 mFuncMap:

void AClass::initFuncMap( )

    mFuncMap[FUNC_TYPES::FUNCTYPE_1] = & AClass::doStuff;

所有编译都很好。

现在我想调用映射函数指针。

我试过这种形式,我知道它适用于不适用于成员函数的函数指针。

mFuncMap[FUNC_TYPES::FUNCTYPE_1]( );

这会产生一个很长的解释性编译器错误:

错误:必须使用'.'或'->'来调用指向成员函数的指针 (AClass*)this)->AClass::mFuncMap.std::map<_key _tp _compare _alloc>...

我几乎尝试了我能想到的所有形式的取消引用,并且我通过搜索找到了 - 带括号,没有它们,等等等等......但我无法获得正确的语法来进行这个调用.

调用映射成员函数的正确语法是什么?我的声明或初始化是否有问题导致此问题?

【问题讨论】:

@user3477950:他可能希望使用this,就像你写doStuff()而不是this-&gt;doStuff()一样。如果您还不知道,这不是一个飞跃。 下次请进一步缩小您的问题范围。这与地图无关,因此地图不应成为问题的一部分。如果你适当地缩小了问题的范围,你最终会意识到它归结为“我如何调用指向成员函数的指针?”然后你可以简单地谷歌它。 @LightnessRacesinOrbit - 他可能希望使用它.. 谢谢。我的想法正是如此:正如我在问题中解释的那样,对于非成员函数指针 () 无需任何进一步的限定即可工作。我认为隐含的 this-> 也会起作用。我没有找到任何其他解释,我确实环顾四周。(我编辑了标题和标签) @Vector:当收到复杂的错误消息时,我建议您将您的陈述分解为多个部分以隔离问题。 TFunc const func = mFuncMap[FUNC_TYPES::FUNCTYPE_1]; func(); 指出问题出在func,而不是mFuncMap,从而使您更接近答案(并减少问题中的混乱)。 @Vector:是的,看过编译器的内部后,我可以向你保证,编写它们的人真的很关心有良好的诊断,但这真的很难,而且经常导致次优诊断.通过简短的陈述,您可以促进他们的工作,因此,您可以(通常)获得更准确的诊断,或者至少可以调查一小段代码:D 【参考方案1】:

这与地图无关,与 typedef 无关。 You have a pointer-to-member-function and you're not invoking it properly.

你需要一个AClass 来运行函数:

AClass& a = someAClassSomewhere();
(a.*(mFuncMap[FUNC_TYPES::FUNCTYPE_1]))();

当然这样真的很丑,所以考虑提前绑定对象:

typedef std::function<void()> TFunc;
std::map<FUNC_TYPES, TFunc> mFuncMap;

// ...

mFuncMap[FUNC_TYPES::FUNCTYPE_1] = std::bind(&AClass::doStuff, this);

// ...

mFuncMap[FUNC_TYPES::FUNCTYPE_1]();

(live demo)

【讨论】:

@Vector:当然可以,and here's a live example to prove it。您引用了result_type 的定义,但这不是std::bind 的返回类型。从您引用的同一参考页面:“未指定类型的函数对象Tstd::is_bind_expression&lt;T&gt;::value == true并且可以存储在std::function中。” 好的 - 我明白了 - 我刚刚运行了你的样本。无法与代码争论。我看到我错误地引用了那里的文档 - result_type 不是 return value。一定是我在搞砸的其他事情。 C++ 对我来说是一种“爱好” - 不支付我的账单 - 我在深夜这样做...... @Vector:我的支付账单并且我很晚才这样做;) 我的日常工作是使用 Delphi 和/或 C# - 做了这么久我可以(并且确实...)在睡梦中做 - 白天... 我节省了我的夜晚有趣。我来自 Dbase/Clipper 世界——下班后我已经搞砸了许多语言,尤其是 Python、Go 和 C++。 C++ 是我不断回归的那个——据我所知,除了 Object Pascal 之外的大多数其他东西只是实现得很差的 C++ 变通方法/子集。 C++ 胜过其他所有东西,但它又大又复杂——不幸的是我没有足够的时间来掌握它来支付账单,但我喜欢学习和探索。 std::function 太好了。取代了对编译器闭包扩展的需求。

以上是关于如何调用成员函数指针?的主要内容,如果未能解决你的问题,请参考以下文章

如何从静态成员函数调用指向成员函数的指针?

c++类的成员函数指针如何转为普通指针

如何通过保存在容器中的成员指针函数调用?

如何调用成员函数指针?

如何从 2 个 void 指针调用类成员函数

C++|详解类成员指针:数据成员指针和成员函数指针及应用场合