我们刚刚在我们的应用程序的 Android 版本中偶然发现了一个错误,该错误是由 iOS 和 Android 上的编译器差异引起的。好奇是否有人可以解释差异以及如何使 Android native C 编译器像 iOS 一样工作。这是问题的简化版本。
double zone = -7 / 24.0;
char command[80] = { '\0' };
//其他东西
command[7] = zone * 24.0;
忽略上述可能的舍入误差。这是一个简化的例子。
在 iOS 上,command[7] 获取输入的值 -7。这是我所期望的,因为在执行分配时应该自动从 double 转换为 char(或 int)。
在 Android 上,使用原生 C 编译器,我们将 0 放入命令 [7]。如果我们像这样显式地转换它
command[7] = (int)(zone * 24.0);
然后得到和iOS一样的结果。
有谁知道为什么这两个编译器会生成不同的代码?如果 Android 上有一个编译器标志可以使编译器的行为与 iOS 中的一样?该应用已经在 iOS 上进行了广泛的测试,我们对这个问题有点怀疑。
在您的 Android C 实现中,char
是无符号的,从 double
中的 -7 到 char
的转换产生零。 (当值不能以目标类型表示时,此转换的行为未由 C 标准定义。)
在 iOS 中,char
是有符号的,double
中的 -7 到 char
的转换产生 -7。
编译器可能有一个 -fsigned-char
开关可以使 char
签名,或者您可以更改 char command[80]…
到 signed char command[80]…
.
这就解释了为什么 command[7] = (int)(zone * 24.0);
会得到想要的结果:
command[7]
之前将结果转换为 int
时,double
中的 -7 将转换为 -7在 int
中。然后这个 int
被转换成一个无符号 char
。该转换由 C 标准定义,结果为 CHAR_MAX+1-7(在典型的 C 实现中使用无符号 char
为 249)。这在 iOS (-7) 和 Android (249) 上的结果不同,但它们用相同的位表示。据推测,无论您进一步使用它们,它们的行为都是相同的。关于android - iOS 和 Android 开发的 C 编译器差异,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21467195/
欢迎光临 OStack程序员社区-中国程序员成长平台 (https://ostack.cn/) | Powered by Discuz! X3.4 |