无符号溢出在C模运算符 [英] unsigned overflow with modulus operator in C

查看:202
本文介绍了无符号溢出在C模运算符的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我遇到了一些C code我写了一个错误,而这是比较容易解决,我希望能够更好地理解它背后的问题。本质上发生了什么事是我有两个无符号整数(uint32_t的,其实),当应用于模操作,得到一个负数,已被包裹了一些未签名等同,是这样的大。下面是一个例子程序来演示:

i encountered a bug in some c code i wrote, and while it was relatively easy to fix, i want to be able to understand the issue underlying it better. essentially what happened is i had two unsigned integers (uint32_t, in fact) that, when the modulus operation was applied, yielded the unsigned equivalent of a negative number, a number that had been wrapped and was thus "big". here is an example program to demonstrate:

#include <stdio.h>
#include <stdint.h>

int main(int argc, char* argv[]) {

  uint32_t foo = -1;
  uint32_t u   = 2048;
  uint64_t ul  = 2048;

  fprintf(stderr, "%d\n", foo);
  fprintf(stderr, "%u\n", foo);
  fprintf(stderr, "%lu\n", ((foo * 2600000000) % u));
  fprintf(stderr, "%ld\n", ((foo * 2600000000) % u));
  fprintf(stderr, "%lu\n", ((foo * 2600000000) % ul));
  fprintf(stderr, "%lu\n", foo % ul);

  return 0;

}

这将产生以下输出,我x86_64的机器上:

this produces the following output, on my x86_64 machine:

-1
4294967295
18446744073709551104
-512
1536
2047

1536年是我期待的数目,但(uint32_t的)( - 512)是我渐渐,其数量,如你所想,扔东西了,有点

1536 is the number i was expecting, but (uint32_t)(-512) is the number i was getting, which, as you might imagine, threw things off a bit.

所以,我想我的问题是:为什么两个无符号数之间的模运算,在这种情况下,生产出一批比除数(即负数)更大?是有这种行为preferred理由吗?

so, i guess my question is this: why does a modulus operation between two unsigned numbers, in this case, produce a number that is greater than the divisor (i.e. a negative number)? is there a reason this behavior is preferred?

推荐答案

我想原因是编译器是跨preting的 26亿文本作为签约64位的数目,因为它不适合成为一个符号的32位int。如果换成 2600000000U 的数量,你应该得到你所期望的结果。

I think the reason is that the compiler is interpreting the 2600000000 literal as a signed 64-bit number, since it does not fit into a signed 32-bit int. If you replace the number with 2600000000U, you should get the result you expect.

这篇关于无符号溢出在C模运算符的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆