22

所以我有一些这样的代码:

void foo (int, int);

void bar ( )
{
    //Do Stuff

   #if (IMPORTANT == 1)
       foo (1, 2);
   #endif

}

在没有“重要”的情况下进行编译时,我得到一个编译器警告 foo 已定义且从未被引用。这让我思考(这就是问题所在)。

所以为了解决这个问题,我只是#if (IMPORTANT == 1)在函数定义等周围添加了相同的内容......以删除警告,然后我开始怀疑是否有不同的方法来抑制该函数上的警告。我正在查看“未使用”的 GCC 属性,但不知道函数是否具有我可以设置的相同属性?是否还有另一种方法来抑制它,只抑制该功能而不是文件的警告?

4

9 回答 9

36

在 C++17 中,您可以使用以下命令声明您的函数[[maybe_unused]]

[[maybe_unused]] void foo (int, int);

这将抑制警告,并且是在 C++17 中表达可能未使用的函数的正确惯用方式。

于 2017-01-09T15:43:11.100 回答
31

我相当确定相关的警告选项是这个:

-Wunused-function
声明静态函数但未定义或未使用非内联静态函数时发出警告。此警告由-Wall 启用。

所以警告应该只针对一个static有趣的功能。说得通。如果一个函数是static它只能在当前文件中使用,那么它的定义也必须在这个文件中。

并且声明它static inline可以避免警告,而无需使用丑陋的宏或编译器特定的编译指示或属性。

于 2012-06-20T18:43:29.853 回答
27

...然后我开始怀疑是否有其他方法可以抑制对该功能的警告。

可能有编译器选项来抑制此警告。然而,一个技巧是这样的:

(void)foo; //cast it to void.

它应该抑制这个警告。

你可以写一个宏:

#define SUPPRESS_WARNING(a) (void)a

void foo(int thisIsAlsoAnUnsedParameter, int usedParameter)
{
   SUPPRESS_WARNING(foo); //better do this inside the definition itself :D

   SUPPRESS_WARNING(thisIsAlsoAnUnsedParameter);
}

如您所见,foo自身的定义抑制了警告。

于 2012-06-20T17:34:07.757 回答
21

一种解决方案是通过函数属性。

void foo (int, int) __attribute__ ((unused));

这将告诉 gcc 不要为该函数发出未使用的函数警告foo。如果您担心可移植性,您可以定义一个宏UNUSED_FUNCTION_ATTRIBUTE,该宏__attribute__ ((unused))使用支持属性的编译器扩展,但在其他情况下扩展为什么都没有。

于 2012-06-20T17:51:13.577 回答
2

封装依赖于编译器和系统的东西的一个好方法是将它分解到头文件中。然后根据编译器和系统以及可能的其他因素调整包含路径。您可以对源代码文件执行相同的操作。

在这种情况下,声明似乎不依赖于编译器或系统,因此只需添加以下公共标头:

// [foo.h]
#pragma once
void foo( int, int );

带实现文件

// [foo.cpp]
#include <foo.virtual.cpp>

然后对于应该发生某些事情的构建,将包含路径添加到包含路径

// [foo.virtual.cpp]
#include <foo.h>
void foo( int const a, int const b )
{
    // Do the thing.
}

对于不应该发生任何事情的构建,将包含的目录添加到包含路径

// [foo.virtual.cpp]
#include <foo.h>
void foo( int, int ) {}

如果您担心空函数的调用会非常耗时,例如浪费一纳秒,那么只需将定义移至标题并添加单词inline.

如果foo也用于其他目的,请定义一个函数bar,为应该或不应该发生的事情调用它,并执行上述 forbar而不是 for foo

然后,您已经删除了所有预处理器的东西。

请记住,代码中的预处理器指令是不好的。

于 2012-06-20T17:52:47.830 回答
2

我找到了一种在全球范围内做到这一点的方法,它也适用于c

#define SUPPRESS_UNUSED_WARN(var) \
    int _dummy_tmp_##var = ((int)(var) & 0)

然后你像这样使用它:

static int foo(int a, int b)
{
    // ....
}
SUPRESS_UNUSED_WARN(foo);
  • 它可以用于函数和全局变量
  • 它应该放在全球范围内才能正常工作
  • 它不能用于局部变量
于 2015-01-30T09:01:08.817 回答
1

对于 ARM 目标平台,在使用 ARM 编译器时,在目标函数周围使用以下编译器指令来抑制“Warning[Pe177]: function declared but never referenced”警告消息:

#pragma diag_suppress=Pe177
void foo(void)
{
/* does something but is not being called for the current build */
}
于 2015-12-02T12:36:44.757 回答
0
#define SUPPRESS_UNUSED_WARN(var) \
    int _dummy_tmp_##var = ((int)(var) & 0)

在 IAR 中不起作用,更改此设置将起作用:

#define SUPPRESS_UNUSED_WARN(var) \
     void _dummy_tmp_##var(void) { (void)(var); }
于 2019-08-17T04:23:44.453 回答
-4

您还可以在 Visual Studio 项目设置中定义 _CRT_SECURE_NO_DEPRECATE 宏。

转到项目属性 -> 配置属性 -> C/C++ -> 预处理器 -> 预处理器定义

添加 _CRT_SECURE_NO_DEPRECATE。

就是这样。!

于 2015-01-30T09:08:37.523 回答