C语言中定点数运算的long long int表示问题
问题分析与修复方案
警告原因
问题根源在1 << 32这行代码:C语言中,字面量1默认是32位int类型(绝大多数现代系统的默认配置),而左移操作的移位位数不能大于等于操作数的类型宽度——左移32位已经超出了32位int的范围,因此gcc会抛出left shift count >= width of type警告,甚至可能触发未定义行为。
反观16.16格式的代码,1 << 16是32位int左移16位,完全在合法范围内,所以没有问题。
修复后的代码
只需要把左移的操作数明确指定为long long类型即可,或者直接用数值赋值,两种方案都能实现你要的00000001.00000000表示:
// 方案1:用long long字面量做左移,符合你的原有写法习惯 static signed long long int varInit = 1LL << 32; unsigned long int integer_part, fractional_part; fractional_part = ((unsigned long int *) &varInit)[0]; integer_part = ((unsigned long int *) &varInit)[1];
// 方案2:直接赋值2^32的数值,更直观且避免移位操作 static signed long long int varInit = 4294967296LL; unsigned long int integer_part, fractional_part; fractional_part = ((unsigned long int *) &varInit)[0]; integer_part = ((unsigned long int *) &varInit)[1];
关键细节说明
1LL是long long类型的字面量,左移32位后,正好对应32.32格式中整数部分为1、小数部分为0的数值(高32位为1,低32位为0)。- 你的代码依赖小端字节序:低地址存储变量的低32位(对应小数部分),高地址存储高32位(对应整数部分)。如果运行在大端系统上,需要调换
integer_part和fractional_part的赋值顺序。
内容的提问来源于stack exchange,提问作者kvirk
相关产品推荐
相关产品推荐

