【发布时间】:2020-12-01 23:14:14
【问题描述】:
我正在开发一个 C 应用程序,我希望它具有合理的可移植性。它可以在 Linux 上使用 gcc 和 clang 以及在 Windows 上使用 MSVC 构建。访问 Mac 后,我尝试使用命令行工具进行构建。
它无法编译,因为我的代码声明了一个函数 isnumber,而 Apple 的 ctype.h 标头也声明了一个(非标准?)isnumber。我可以重命名我的函数,这样它就不会发生冲突,但是有没有办法通过禁用或忽略所有或特定的 Apple 对标准头文件的添加来避免这种情况?例如。是否有编译器选项或预处理器编译指示可以忽略它们?
我的isnumber 无法检查字符类。下面是重现该问题的代码 - 它可以使用 clang/Linux 和 MSVC/Windows 编译,但不能在 Mac 上编译(-它不是实际代码)。
#include <ctype.h>
#include <stdio.h>
char *isnumber(void);
int main(void)
{
char *opt = "A";
if (isupper(*opt))
printf("THE IS NUMBER IS: %s\n", isnumber());
else
printf("The IS number is: %s\n", isnumber());
return 0;
}
char *isnumber(void)
{
return "IS-123";
}
错误:
/Users/ ... /repro/main.c:4:7: error: conflicting types for 'isnumber'
char *isnumber(void);
^
/Library/Developer/CommandLineTools/SDKs/MacOSX.sdk/usr/include/_ctype.h:323:1: note: previous definition is here
isnumber(int _c)
更新:
正如 Acorn 的回答和它的 cmets 所描述的,“isnumber”是函数的错误名称,因为 C11 标准保留它:
7.31 未来图书馆方向
为方便起见,以下名称分组在各个标题下。 下面描述的所有外部名称都是保留的,无论程序包含什么标头。...
7.31.2 字符处理
<ctype.h>
"以is或to开头的函数名称和一个小写字母可以添加到<ctype.h>标头中的声明中。
因此,我原来的问题的“正确”解决方案是重命名 my 函数。
【问题讨论】:
-
重命名函数有什么问题?也许你的项目是 50,000 行,你需要 30 分钟来替换所有调用...
-
你试过用
-std=c11编译吗? -
@FelixG 我刚刚用 c89、c99、c11 和 c17 尝试了 -std=,结果相同。
-
你看头文件有没有
#ifdefs关于那些函数? -
@FelixG 我之前做过,但再看看可能会有希望......会尝试一些事情并报告。
标签: c clang c-standard-library xcode-command-line-tools