乍一看,这个问题看起来像是如何检测整数溢出的重复?然而,它实际上是显着不同的.
我发现虽然检测无符号整数溢出非常简单,但在C/C++中检测带符号的溢出实际上比大多数人想象的要困难.
最明显但又天真的方式是这样的:
int add(int lhs, int rhs)
{
int sum = lhs + rhs;
if ((lhs >= 0 && sum < rhs) || (lhs < 0 && sum > rhs)) {
/* an overflow has occurred */
abort();
}
return sum;
}
Run Code Online (Sandbox Code Playgroud)
这个问题是根据C标准,有符号整数溢出是未定义的行为. 换句话说,根据标准,只要您甚至导致签名溢出,您的程序就像取消引用空指针一样无效.因此,您不能导致未定义的行为,然后尝试在事后检测溢出,如上面的后置条件检查示例.
尽管上面的检查很可能适用于许多编译器,但你不能指望它.实际上,因为C标准说未定义有符号整数溢出,所以一些编译器(如GCC)将在设置优化标志时优化上述检查,因为编译器假定有符号溢出是不可能的.这完全打破了检查溢出的尝试.
因此,检查溢出的另一种可能方法是:
int add(int lhs, int rhs)
{
if (lhs >= 0 && rhs >= 0) {
if (INT_MAX - lhs <= rhs) {
/* overflow …Run Code Online (Sandbox Code Playgroud) 我很想知道如果我给无符号变量赋一个负值会发生什么.
代码看起来有点像这样.
unsigned int nVal = 0;
nVal = -5;
Run Code Online (Sandbox Code Playgroud)
它没有给我任何编译器错误.当我运行程序时,nVal分配了一个奇怪的值!是否可以将某个2的补码值分配给nVal?
假设我有这个号码i = -6884376.我如何将其称为无符号变量?像(unsigned long)iC中的东西
当我从调试映射键切换到我签名的地图键时,我的地图停止工作.我在logcat中遇到以下错误:
09-03 18:18:04.112: WARN/System.err(4073): IOException processing: 26
09-03 18:18:04.112: WARN/System.err(4073): java.io.IOException: Server returned: 3
09-03 18:18:04.112: WARN/System.err(4073): at android_maps_conflict_avoidance.com.google.googlenav.map.BaseTileRequest.readResponseData(BaseTileRequest.java:115)
09-03 18:18:04.112: WARN/System.err(4073): at android_maps_conflict_avoidance.com.google.googlenav.map.MapService$MapTileRequest.readResponseData(MapService.java:1473)
09-03 18:18:04.112: WARN/System.err(4073): at android_maps_conflict_avoidance.com.google.googlenav.datarequest.DataRequestDispatcher.processDataRequest(DataRequestDispatcher.java:1117)
09-03 18:18:04.112: WARN/System.err(4073): at android_maps_conflict_avoidance.com.google.googlenav.datarequest.DataRequestDispatcher.serviceRequests(DataRequestDispatcher.java:994)
09-03 18:18:04.112: WARN/System.err(4073): at android_maps_conflict_avoidance.com.google.googlenav.datarequest.DataRequestDispatcher$DispatcherServer.run(DataRequestDispatcher.java:1702)
09-03 18:18:04.112: WARN/System.err(4073): at java.lang.Thread.run(Thread.java:1019)
Run Code Online (Sandbox Code Playgroud)
我已经仔细检查了所有内容,权限和库已经到位.我重新创造了烧焦的钥匙而没有运气.
有任何想法吗?
在Java中,没有无符号字节.
使用某些低级代码时,有时需要处理大于128的无符号值的字节,这会导致Java将其解释为负数,因为MSB用于符号.
解决这个问题的好方法是什么?(说不要使用Java不是一个选项)
我有一个用于在C中实现的编程语言的VM.它支持在32位和64位架构以及C和C++下编译.
我正在尝试使用尽可能多的警告来干净地编译它.当我打开时CLANG_WARN_IMPLICIT_SIGN_CONVERSION,我会得到一连串的新警告.
我希望有一个很好的策略,可以使用何时使用int显式无符号类型和/或显式大小的类型.到目前为止,我无法确定该策略应该是什么.
将它们混合使用 - 主要int用于局部变量和参数之类的东西,并在结构中使用较窄的类型- 确实会导致许多隐式转换问题.
我喜欢为struct字段使用更具体的大小类型,因为我喜欢显式控制堆中对象的内存使用量的想法.此外,对于散列表,我在散列时依赖于无符号溢出,因此如果散列表的大小存储为,则很好uint32_t.
但是,如果我尝试在任何地方使用更具体的类型,我发现自己到处都是曲折的迷宫.
其他C项目有什么作用?
我无法导出已签名或未签名的应用程序包
http://imageshack.us/photo/my-images/163/imagewgnb.jpg/
*Export Aborted
Export aborted because fatal Lin error were founds. These are listed in the
problems view. Either fix these before running Export Again, or turn off "Run
full error check when exporting app" in the Android > Lint Error Cheking preference page.*
Run Code Online (Sandbox Code Playgroud)
方案:
Window>Preferences>Android>Lint Error Checking
uncheck Run full error check when exporting app
Run Code Online (Sandbox Code Playgroud) int main(void)
{
unsigned int y = 10;
int x = – 4;
if (x > y)
Printf("x is greater");
else
Printf("y is greater");
getch();
return (0);
}
Output: x is greater
Run Code Online (Sandbox Code Playgroud)
我认为输出y会更大,因为它是无符号的.这背后的原因是什么?
请参阅此代码段
int main()
{
unsigned int a = 1000;
int b = -1;
if (a>b) printf("A is BIG! %d\n", a-b);
else printf("a is SMALL! %d\n", a-b);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
这给出了输出:a是SMALL:1001
我不明白这里发生了什么.>运算符如何在这里工作?为什么"a"小于"b"?如果它确实更小,为什么我得到一个正数(1001)作为差异?
C标准明确规定有符号整数溢出具有未定义的行为。然而,大多数CPU都使用定义的语义为溢出实现签名算法(可能除法除法溢出为:x / 0和INT_MIN / -1)。
编译器的作家一直在走的优势undefinedness这种溢出的补充,往往会打破传统的代码非常微妙的方式更积极的优化。例如,此代码可能在较旧的编译器上有效,但在gccand的当前版本上不再有效clang:
/* Tncrement a by a value in 0..255, clamp a to positive integers.
The code relies on 32-bit wrap-around, but the C Standard makes
signed integer overflow undefined behavior, so sum_max can now
return values less than a. There are Standard compliant ways to
implement this, but legacy code is what it is... */
int sum_max(int a, unsigned char b) {
int …Run Code Online (Sandbox Code Playgroud)