C++中的'new'关键字和C

6

可能重复:
在C ++中将关键字class用作变量名

我正在使用一个库的C头文件,其中一个变量被命名为“new”。不幸的是,我正在一个C ++项目中使用这个库,'new'作为变量名称的出现使编译器崩溃。我已经使用了extern "C" { #include<...> },但这似乎对此没有帮助。

即使从C开发人员的角度来看,'new'不是C关键字,库开发人员也必须更改该变量的名称吗?


1
一个库开发者决定将一个全局变量命名为 new - dreamlax
1
我认为这基本上是 https://dev59.com/3nE85IYBdhLWcg3wUBoZ 的重复。 - sbi
该死。你是怎么找到那个问题的,sbi?我真的在发帖之前努力寻找答案,但从未遇到过那个问题。 - Florian
别担心,我最近还记得这个问题(虽然我不记得是哪个关键字),但即使使用了SO的搜索功能,我仍然尝试了几次才找到它。最后,我认为“包括头文件关键字”让它在前六个结果中显示出来,但我不确定... - sbi
我仍然保留着搜索的标签,所以我可以确定:_包含“C”头文件“C ++”关键字_(我不确定引号是否会改善搜索,在谷歌中是这样的,所以它们在我的肌肉记忆中)。 - sbi
4个回答

9
在包含头文件之前,使用预处理器重命名new:
#define new mynew
#include <...>
#undef new

这将允许编译继续进行。

你实际上需要访问这个变量吗?如果不需要-那么你完成了。如果需要,那么你需要确保库的.c文件是使用编译器编译的。

-Dnew=mynew

然后希望没有已经存在名为 mynew 的变量 :) - dreamlax
我不需要访问它,它只是一个函数声明中的参数。我明白你的意思:因为预处理器将“new”替换为“mynew”,C++编译器永远不会看到头文件中的“new”,而只会看到“mynew”,这不是C++关键字,因此可以使用。 - Florian
回答dreamlax的问题:只有使用“-Dnew=mynew”部分才会造成问题。第一部分应该是完全正常的,在我的情况下足够了。 - Florian
@Florian:是的,完全正确!@dreamlax::) - psmears

3
头文件是否需要包含此变量的名称?如果您正在使用名为“new”的全局变量,则当然需要具有全局可见的变量名称。另一方面,如果这是一个名为“new”的函数参数,只需从函数声明中删除名称即可。如果名称是结构或联合体的成员,则在头文件中更改它不会损害.C代码,只要.C代码看到与源代码匹配的“私有”定义即可。
由于.C文件应以C语法编译,因此可以处理名为“new”的变量,修复头文件应该是有效的解决方法。
从长远来看,是的,您应该引起库开发人员的注意。
作为最终的,有些hacky的解决方案,您可以将头文件从“new”更改为其他内容,例如“was_new”。并且在编译库的C文件时使用编译器开关来强制使用#define new was_new

我知道我可以简单地删除或重命名那个变量,因为它只在函数声明中使用。我正在寻找一个解决方案,使库的C头文件保持不变。如果我的表述不够清晰,我很抱歉。感谢您的回答。最终,我改变了头文件,并将与库开发人员联系。 - Florian

1

您可以在C中编写自己的包装函数。您使用的所有与库相关的内容都将使用C编写,并具有C++友好的头文件。因此,不要像下面这样:

other_lib.h:
int foo( int new );
my_app.cxx: extern "C" { #include <other_lib.h> }

这样是无法编译的,您需要这样做:

my_wrap.h:
#ifdef __cplusplus
extern "C" {
#endif
int my_foo( int );
#ifdef __cplusplus
}
#endif
my_wrap.c: #include <other_lib.h> int my_foo( int x ) { return foo( x ); }
my_app.cxx: #include "my_wrap.h"
...

使用C编译器编译my_wrap.c,然后使用C++编译器编译my_app.cxx。 这样可以在不对现有库进行任何更改的情况下构建。


0

如果您正在修改第三方库的完好无损的头文件,我建议您现在停止。如果我理解正确,您正在尝试向C库添加C++代码,这是不行的,因为C不认识“new”关键字,它是C++关键字。

相反,我建议:

您可以创建一个单独的C++项目,其中包含一个源文件(*.cpp),将第三方头文件添加到其中,并将库的二进制文件链接(谷歌“链接库”等)到您的项目中。

希望这有点帮助, 祝好


实际上,我不想修改C头文件,因为它是库的一部分。我正在寻找的解决方案仅依赖于更改我的自己的C++源代码。问题不在于链接库,而是编译我的项目的C++源代码,因为它仍然包含来自库的C头文件,并且那些头文件虽然是有效的C,但不是有效的C ++。 - Florian

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接