是否可以检查名称为字符串的函数是否存在?(C++)

Posted

技术标签:

【中文标题】是否可以检查名称为字符串的函数是否存在?(C++)【英文标题】:Is it possible to check if a function with a string as its name exists?(C++) 【发布时间】:2011-08-18 04:24:57 【问题描述】:

我希望能够做这样的事情:

if (Is_Function("helloworld")
    // Run code

【问题讨论】:

没有。你为什么要这样做?可能还有其他方法。 这在 Lua 等脚本语言中是可能的,并且您可能能够通过反射在 Java 或 C# 等语言中做一些棘手的事情,但在 C++ 中绝对不可能除非您已经完成了将字符串映射到函数指针之类的操作。你为什么要这样做?几乎可以肯定,无论您遇到什么问题,都有更好的解决方案。 确切的问题是什么?你想知道一个函数名helloworld()是否存在? // Run code 包含什么?如果它包含对helloworld() 的调用,那么你最好有一个可用函数的声明,否则你只会得到一个编译错误。如果你有一个声明,那么你就知道它存在(或者链接器会告诉你如果它不存在)。 为什么在 C++ 世界中有人要求这样做?在 13 年的 C++ 工作中,我从未想过要做这样的事情,也没有遇到任何需要这样做的情况。您到底在寻找什么? 【参考方案1】:

简单的回答:没有

复杂的答案:是的,如果打开了调试符号并且您编写了一些帮助函数来查看调试符号。但这真的很可怕,有问题(函数可以自动内联,并且会神奇地从您的符号表中消失),而且一旦您构建程序的发布版本,大多数功能就会停止工作。

最终答案:

【讨论】:

【参考方案2】:

不是一般意义上的,因为 C++ 不支持反射。您可以使用调试信息编译程序并让它自己打开并像调试器一样读取其符号表,但这可能比它的价值更麻烦。

无论如何,为什么需要在运行时检测函数的存在?这在编译时就知道了。

如果您可以将可能包含函数的部分分离到动态库中,则可以在运行时打开它并对其进行符号查找。 (在 Linux 系统上,您将使用 dlopen()dlsym();在其他平台上也有等价物,但我不知道它们的名称。)这将告诉您名称是否作为符号存在,尽管它不会t 告诉你它是否是一个函数。

【讨论】:

【参考方案3】:

您可以在基于 ELF 的系统(Linux 和大多数 Unix 变体,包括 MacOS X)上使用的一种技术是与 -rdynamic 链接,然后调用 dlsym(RTLD_DEFAULT, "helloworld") 以获取指向函数 helloworld 的指针,如果它存在于当前可执行文件或任何已加载的共享库中。由于名称修改,这在 C++ 中存在问题,因此实际上仅适用于使用 extern "C" 或在 C 代码中声明的函数。

【讨论】:

+1。这正是如何做到的;在运行时加载共享库并且事先不知道是否会存在某些功能时,我已经看到它在愤怒中完成。这允许定义回退。任何人都知道 Windows 等价物吗?【参考方案4】:

好吧,Qt 在使用信号和槽时会做类似的事情,但是这些函数将被注册到一个映射中,该映射由它们的名称 iirc 的修饰索引。这种注册是通过他们的“MetaObject Compiler”实现的,它基本上是一个预处理器/代码生成器,并且静态工作。

根据你想做什么,你可以使用 Qt。

另一种可能性是编译一个共享库并使用 dlsym,如果在您的系统上可用的话。

【讨论】:

以上是关于是否可以检查名称为字符串的函数是否存在?(C++)的主要内容,如果未能解决你的问题,请参考以下文章

当我只知道部分名称时检查是不是存在临时表?

我可以键入检查模板参数吗? (C++)[重复]

C++的fstream如何检查一个文件是不是成功打开?

C语言,判断一个文件是不是存在

是否可以随机设置文档中尚不存在的名称?

检查动态组件是不是存在