C++ 编译时检查函数是否已使用/未使用c++;
我想在编译期间检查某个类的某些函数是否被使用/未被使用,并相应地使编译过程失败/通过 例如,如果在代码中的某个地方调用了函数C++ 编译时检查函数是否已使用/未使用c++;,c++,templates,c-preprocessor,metaprogramming,code-generation,C++,Templates,C Preprocessor,Metaprogramming,Code Generation,我想在编译期间检查某个类的某些函数是否被使用/未被使用,并相应地使编译过程失败/通过 例如,如果在代码中的某个地方调用了函数F1,我希望编译成功,如果调用了函数F2,我希望编译失败 关于如何使用预处理器、模板或其他C++元编程技术(> P>),你可以用C++ 11编译器实现这一点,只要你愿意修改F2在函数体中包含STATISHYSART,并在签名中添加一个哑模板: #include <type_traits> void F1(int) { } template <t
F1
,我希望编译成功,如果调用了函数F2
,我希望编译失败
关于如何使用预处理器、模板或其他C++元编程技术(
> P>),你可以用C++ 11编译器实现这一点,只要你愿意修改F2在函数体中包含STATISHYSART,并在签名中添加一个哑模板:#include <type_traits>
void F1(int) {
}
template <typename T = float>
void F2(int) {
static_assert(std::is_integral<T>::value, "Don't call F2!");
}
int main() {
F1(1);
F2(2); // Remove this call to compile
}
#包括
空F1(int){
}
模板
空F2(整数){
静态断言(std::is_integral::value,“不要调用F2!”);
}
int main(){
F1(1);
F2(2);//删除此编译调用
}
如果没有F2的呼叫者。请参阅,了解为什么我们需要模板技巧,而不能简单地插入
static_断言(false)(“”)代码>不是一个非常模板化的解决方案,但您可以依赖编译器的弃用属性,该属性将在任何地方使用函数时生成警告
如果是MSVC,则使用属性:
__declspec(deprecated("Don't use this")) void foo();
G++:
如果您有“将警告视为错误”编译选项(您通常应该这样做),您将获得所需的行为
int main()
{
foo(); // error C4966: 'foo': Don't use this
return 0;
}
“如果称为F1,它将成功”是一个奇怪的要求。你的意思是:“如果不调用F1,它将无法编译”@JoachimPileborg Ahm,很公平,我收回了我的评论。重命名函数,链接器将告诉你是否使用了它。编译器无法判断是否调用了外部函数,只能判断当前正在编译的翻译单元中定义的函数。我还没有找到任何合适的命令行选项(-Wunused函数
只警告非内联静态
函数)。我也没有在链接器标志中看到任何合适的内容。您可能需要让链接器创建一个映射文件,如果该文件包含该信息,则解析该文件并发出生成过程错误。您能告诉我们更多有关为什么需要该文件的信息吗?我很确定对于实际问题有更好的解决办法。。。。并删除F2
的旧实现。无需删除旧实现,只需修改现有实现即可。。。。并将其移动到标题处。如果不这样做,您将在调用站点(而不是static\u assert
firing)得到未定义模板的错误。对于“如果调用了F2
则编译时错误”仍然足够好,我猜。同意;我忘了在我的例子中考虑到这一点。根据@mah的注释重命名函数以实现编译时错误可能不那么麻烦。。。让这更复杂一点怎么样:-)假设我有一组函数F1…Fn和一组类C1…Cm有没有办法让代码在已知规则集下编译/不编译,其中每个类Ci只允许调用函数F1…Fn的子集(每个类有不同的子集。这也使得事情变得更加复杂,如果我想要稳健性怎么办。意思是确保从某个地方调用某个函数。
int main()
{
foo(); // error C4966: 'foo': Don't use this
return 0;
}