C++编译器如何在二进制代码中表示整数?

3

我写了一个程序,使用C++中的位运算符来展示特定整数值的二进制表示。对于偶数它按照我的预期工作正常,但是对于奇数,它会在二进制表示的左边加上1。

#include <iostream>

using std::cout;
using std::cin;
using std::endl;

int main()
{
    unsigned int a = 128;

    for (int i = sizeof(a) * 8; i >= 0; --i) {
        if (a & (1UL << i)) { // if i-th digit is 1
            cout << 1;        // Output 1
        }
        else {
            cout << 0;        // Otherwise output 0
        }
    }
    cout << endl;

    system("pause");

    return 0;
}

结果:

  • 当 a = 128 时:000000000000000000000000010000000,
  • 当 a = 127 时: 100000000000000000000000001111111。

你的第一个移位将是32(假设是32位整数)。这太多了。 - Mat
2个回答

4
  1. 您可能更喜欢使用CHAR_BIT宏而不是原始的8 (#include <climits>)。
  2. 请考虑您的起始值!假设unsigned int有32位,您的起始值为int i=4*8,因此1U << i将值移出范围。这是未定义行为,可能会导致任何结果,显然,您特定的编译器或硬件将shifts %32,因此您得到一个初始的value & 1,导致意外的前导1... 您是否注意到您实际上打印了33个数字,而不仅仅是32个?

1
由于偶数的最低有效位为0,因此请注意,在第一个循环运行中,由于溢出,您应该检查它而不是最高有效位。 - Aconcagua
很抱歉,现在我明白了。我只是忘记了编号位从0开始。因此,要检查最左边的位,我必须将i设置为sizeof(a)*CHAR_BIT-1,以便将1UL左移31个位置。现在它运行得非常好!谢谢 - Влад Казимиров

2

1
一方面,我喜欢它的整洁性,另一方面,我不喜欢循环体与条件检查使用不同的值... 不过,还是很整洁和有见地的。 - StoryTeller - Unslander Monica
优雅的解决方案,我喜欢它,当我理解它时,但它并不是那么清晰。 - Влад Казимиров
1
@StoryTeller 现在你提到了,我看到了将计数和位索引的问题混合在一起的哲学问题。我从30多年前的K&R书中学习了C语言,在那之前是汇编语言。我想老习惯难改。 :) - Richard Hodges

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接