我需要在项目中使用popen
,但我得到:
error: 'popen' was not declared in this scope
看起来GCC在__STRICT_ANSI__
下定义-std=c++0x
并且(与我能够找到的信息相反)-std=gnu++0x
,导致popen
(和{{ 1}})从_popen
中删除。奇怪的是,取消定义stdio
并没有解决问题,也没有向前宣布该功能。我显然错过了一些东西。有合理的解决方法吗?
我正在使用MinGW和4.5.0,并升级到4.5.2,但我仍然遇到同样的问题。我不想用msys来编译4.6.0,但如果必须的话,我会这样做。
答案 0 :(得分:28)
我只是立即在命令行上取消它,这不是非常“干净”,但它可以正常工作。
-std=gnu++0x -U__STRICT_ANSI__
可能有一个很好的理由为什么不应该这样做,但它给了我想要的东西(C ++ 0x加上GNU扩展,加上传统的东西仍然有用)。我已经做了很长时间了,从来没有遇到过麻烦。但如果它吃了你的猫,不要怪我。
答案 1 :(得分:8)
我测试了MinGW gcc 4.6.1和gcc 4.7.0:它们都为__STRICT_ANSI__
定义了-std=c++0x
,但没有为-std=gnu++0x
定义它。
答案 2 :(得分:2)
问题的简短回答
如何让C ++ 0x和__STRICT_ANSI__相处?
应该是:使用-std=gnu++0x
代替-std=c++0x
。这应该不定义__STRICT_ANSI__
[1] ,因此您Makefile
或构建环境中的其他内容可能仍会导致此问题定义 [2] 。
-U__STRICT_ANSI__
取消定义。
请注意,为了指定为您的代码编写的C标准,-std=gnu++*
将是典型的开关,而不是-std=c++*
,只要您想要GNU扩展(在{{1 ,默认情况下启用GNU扩展,但如果指定gcc
,则会禁用。
另一个说明;对于C,这是类似的:
-std=c++*
您可以获得所需C版本的语言支持,无论是否定义$ touch empty.c
$ gcc -std=c99 -E -dM empty.c | grep '\(__STRICT\|__STDC_V\)'
#define __STRICT_ANSI__ 1
#define __STDC_VERSION__ 199901L
$ gcc -std=gnu99 -E -dM empty.c | grep '\(__STRICT\|__STDC_V\)'
#define __STDC_VERSION__ 199901L
(也可能存在其他差异)。
<强> [1]:强>
来自https://gcc.gnu.org/onlinedocs/cpp/Common-Predefined-Macros.html:
__ STRICT_ANSI __
当且仅当在调用GCC时指定-ansi开关或指定严格符合某些版本的ISO C或ISO C ++ 的-std开关时,GCC才定义此宏。它被定义为'1'。该宏的存在主要是为了指导GNU libc的头文件将它们的定义限制在1989 C标准中的最小集合。
这种情况很容易确认(在__STRICT_ANSI__
4.8.2上运行):
gcc
[2]:或许添加$ touch empty.cpp
$ gcc -std=c++0x -E -dM empty.cpp | grep '__STRICT'
#define __STRICT_ANSI__ 1
$ gcc -std=gnu++0x -E -dM empty.cpp | grep '__STRICT'
$ # (no match)
转换的东西?这将产生-ansi
,即使指定__STRICT_ANSI__
,如文档中所述(参见上面的引文),并且可以轻松检查:
-std=gnu++*