将整数转换为二进制并将其存储在指定大小的整数数组中:c ++

7

我想将一个整数转换为二进制字符串,并将整数字符串的每一位存储到给定大小的整数数组的一个元素中。我确定输入整数的二进制表达式不会超过指定数组的大小。如何在C++中实现这个功能?


你为什么想这样做呢?整数已经本地化为"一组位数组",你可以访问每个位。 - Mat
1
“二进制字符串”?就是由1和0组成的字符吗?多么奇怪的任务…… - Mooing Duck
1
@MooingDuck:我明白了。这就像是增加了32倍或64倍的存储空间。但这并没有改变我的问题。 - Mat
@MooingDuck:确切地说,有很多潜在的原因,其中一些可能是合法的,一些可能有更好的替代方案。你不认为回答 OP 实际问题的答案会更好吗? - Mat
1
数组中的 LSB 是先放还是后放? - James
显示剩余3条评论
8个回答

12

伪代码:

int value = ????  // assuming a 32 bit int
int i;

for (i = 0; i < 32; ++i) {
    array[i] = (value >> i) & 1;
}

4
为什么不使用 array[i] = (theValue >> i) & 1 这样的写法呢?我相信编译器会做同样的优化,但是看到“这里不会有分支”的说法让我更加欣慰。 - Mats Petersson
5
这个问题被标记为C ++,所以您必须使用模板,否则就是C。 - James
运行良好,但是位的顺序被颠倒了,所以建议使用索引array[31 - i]而不是array [i]。 - Marek
可以将32更改为sizeof(int) * 8。 - jin zhenhui
@jinzhenhui 我的回答(8年前)是伪代码,如所示。在实际编写时可以应用几种不同的变化,包括您的建议--但我不会字面上使用sizeof(int)。相反,我会使用sizeof(value),它目前确实是相同的。指定变量而不是其类型的好处是,如果变量类型将来发生更改,您只需要直接更改其类型,其他知道该变量的事物不会出现故障或需要更改。 - mah

7

您可以使用C++的位集库,如下所示。

#include<iostream>
#include<bitset>

int main()
{
  int N;//input number in base 10
  cin>>N;
  int O[32];//The output array
  bitset<32> A=N;//A will hold the binary representation of N 
  for(int i=0,j=31;i<32;i++,j--)
  {
     //Assigning the bits one by one.
     O[i]=A[j];
  }
  return 0;
}

这里有几点需要注意: 首先,在bitset声明语句中的32告诉编译器你想用32位来表示你的数字,所以即使你的数字只需要少于32位的位数来表示,bitset变量也会有32位,可能有很多前导零。 其次,bitset是一种处理二进制的非常灵活的方式,你可以将字符串或数字作为其输入,并且可以将bitset作为数组或字符串使用。它是一个非常方便的库。 你可以将bitset变量A打印出来 cout< 看看它是如何工作的。

1
那是个好主意。尽管它与我的竞争,但我还是点赞了。但是为什么你只支持21位数字?为什么不支持32位呢? - Mooing Duck
好的,那让我们把它变成32。 - Aravind

6
template<class output_iterator>
void convert_number_to_array_of_digits(const unsigned number, 
         output_iterator first, output_iterator last) 
{
    const unsigned number_bits = CHAR_BIT*sizeof(int);
    //extract bits one at a time
    for(unsigned i=0; i<number_bits && first!=last; ++i) {
        const unsigned shift_amount = number_bits-i-1;
        const unsigned this_bit = (number>>shift_amount)&1;
        *first = this_bit;
        ++first;
    }
    //pad the rest with zeros
    while(first != last) {
        *first = 0;
        ++first;
    }
}

int main() {
    int number = 413523152;
    int array[32];
    convert_number_to_array_of_digits(number, std::begin(array), std::end(array));
    for(int i=0; i<32; ++i)
        std::cout << array[i] << ' ';
}

Proof of compilation here


你的意思不是 (number >> i) & 1 吗? - James
1
@James:谢谢。首先我发布了代码,然后发布了可以编译的代码,现在它可以编译和执行,并且“似乎”正在工作。 - Mooing Duck

2
你可以这样做:
while (input != 0) {

        if (input & 1)
            result[index] = 1; 
        else
            result[index] =0;
   input >>= 1;// dividing by two
   index++;
}

1
我认为那不太对... (1) 你似乎从未改变索引, (2) 即使那样仍是错误的。 - Mooing Duck

1

十进制转二进制:大小无关

两种方法:都将二进制表示存储到动态分配的数组bits中(从高位到低位)。

第一种方法:

#include<limits.h> // include for CHAR_BIT
int* binary(int dec){
  int* bits = calloc(sizeof(int) * CHAR_BIT, sizeof(int));
  if(bits == NULL) return NULL;
  int i = 0;

  // conversion
  int left = sizeof(int) * CHAR_BIT - 1; 
  for(i = 0; left >= 0; left--, i++){
    bits[i] = !!(dec & ( 1u << left ));      
  }

  return bits;
}

第二种方法:

#include<limits.h> // include for CHAR_BIT
int* binary(unsigned int num)
{
   unsigned int mask = 1u << ((sizeof(int) * CHAR_BIT) - 1);   
                      //mask = 1000 0000 0000 0000
   int* bits = calloc(sizeof(int) * CHAR_BIT, sizeof(int));
   if(bits == NULL) return NULL;
   int i = 0;

   //conversion 
   while(mask > 0){
     if((num & mask) == 0 )
         bits[i] = 0;
     else
         bits[i] = 1;
     mask = mask >> 1 ;  // Right Shift 
     i++;
   }

   return bits;
}

1
如Mat在上面提到的,一个int已经是一个位向量(使用位运算,您可以检查每个位)。因此,您可以尝试像这样简单地执行操作:
// Note: This depends on the endianess of your machine
int x = 0xdeadbeef; // Your integer?
int arr[sizeof(int)*CHAR_BIT];
for(int i = 0 ; i < sizeof(int)*CHAR_BIT ; ++i) {
  arr[i] = (x & (0x01 << i)) ? 1 : 0; // Take the i-th bit
}

已经进行了更正 - 谢谢 ;) (总是忘记 CHAR_BIT - RageD

0

这是我使用的,它还允许您指定最终向量中将包含的位数,并用前导0填充任何未使用的位。

std::vector<int> to_binary(int num_to_convert_to_binary, int num_bits_in_out_vec)
{
    std::vector<int> r;

    // make binary vec of minimum size backwards (LSB at .end() and MSB at .begin())
    while (num_to_convert_to_binary > 0)
    {
        //cout << " top of loop" << endl;
        if (num_to_convert_to_binary % 2 == 0)
            r.push_back(0);
        else
            r.push_back(1);
        num_to_convert_to_binary = num_to_convert_to_binary / 2;
    }

    while(r.size() < num_bits_in_out_vec)
        r.push_back(0);

    return r;
}

0

我知道它不能为正数添加像您希望的那样多的零。但对于负二进制数,它运作得非常好。我只是想发布一种解决方案 :)

int BinToDec(int Value, int Padding = 8)
{
    int Bin = 0;

    for (int I = 1, Pos = 1; I < (Padding + 1); ++I, Pos *= 10)
    {
        Bin += ((Value >> I - 1) & 1) * Pos;
    }
    return Bin;
}

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