我一直试图使用 C编程
打印出长整数的二进制表示我的代码是
#include<stdio.h>
#include <stdlib.h>
#include<limits.h>
int main()
{
long long number, binaryRepresentation = 0, baseOfOne = 1, remainder;
scanf("%lld", &number);
while(number > 0) {
remainder = number % 2;
binaryRepresentation = binaryRepresentation + remainder * baseOfOne;
baseOfOne *= 10;
number = number / 2;
}
printf("%lld\n", binaryRepresentation);
}
当我提供 5 的输入时上述代码正常工作,当数字 9223372036854775807 (0x7FFFFFFFFFFFFFFF)时失败。
1.Test Case
5
101
2.Test Case
9223372036854775807
-1024819115206086201
答案 0 :(得分:2)
使用一个否定数字来表示二进制数字永远不会特别好:你会因为一个非常小的输入而容易溢出,所有后续的算术操作都将毫无意义。
另一种方法是在出发时打印出数字,但使用递归技术,以便按照与处理数字相反的顺序打印数字:
#include <stdio.h>
unsigned long long output(unsigned long long n)
{
unsigned long long m = n ? output(n / 2) : 0;
printf("%d", (int)(n % 2));
return m;
}
int main()
{
unsigned long long number = 9223372036854775807;
output(number);
printf("\n");
}
输出:
0111111111111111111111111111111111111111111111111111111111111111
我还将类型更改为unsigned long long
,其具有更好的定义位模式,%
无论如何都为负数做了奇怪的事情。
实际上,我在这里所做的就是滥用堆栈作为存储真正的零和一组数据的方式。
答案 1 :(得分:1)
只是说明一些注释,最简单的方法是使用char
数组来保存二进制数字。此外,在处理位时,逐位运算符更清晰一些。否则,我保留了你的基本代码结构。
int main()
{
char bits[64];
int i = 0;
unsigned long long number; // note the "unsigned" type here which makes more sense
scanf("%lld", &number);
while (number > 0) {
bits[i++] = number & 1; // get the current bit
number >>= 1; // shift number right by 1 bit (divide by 2)
}
if ( i == 0 ) // The original number was 0!
printf("0");
for ( ; i > 0; i-- )
printf("%d", bits[i]); // or... putchar('0' + bits[i])
printf("\n");
}
答案 2 :(得分:1)
如Bathsheba's answer所述,您需要更多空间 如果您使用十进制数来表示类似的位序列,则可用。
由于您打算打印结果,因此最好一次只执行一次。我们可以通过创建仅具有最高位设置的掩码来实现此目的。为任何类型创建它的神奇之处在于补充该类型的零以获得&#34;所有类型&#34;数;然后我们减去一半(即1111 .... - 0111 ....)只得到一个位。然后我们可以沿着数字向右移动以依次确定每个位的状态。
这是使用该逻辑的重新制作版本,其他更改如下:
printf
)打印的字符数。#include <stdio.h>
#include <stdlib.h>
int print_binary(unsigned long long n)
{
int printed = 0;
/* ~ZERO - ~ZERO/2 is the value 1000... of ZERO's type */
for (unsigned long long mask = ~0ull - ~0ull/2; mask; mask /= 2) {
if (putc(n & mask ? '1' : '0', stdout) < 0)
return EOF;
else
++printed;
}
return printed;
}
int main(int argc, char **argv)
{
for (int i = 1; i < argc; ++i) {
print_binary(strtoull(argv[i], 0, 10));
puts("");
}
}
读者练习:
1
,或者在打印前有一个单独的循环来移动蒙版)。别忘了检查print_binary(0)
是否仍然产生输出!strtoull
转换十进制字符串的输入值时检查错误。答案 3 :(得分:0)
我不确定你真正想要实现的目标,但是这里有一些代码可以打印数字的二进制表示(将typedef
更改为你想要的整数类型):
typedef int shift_t;
#define NBITS (sizeof(shift_t)*8)
void printnum(shift_t num, int nbits)
{
int k= (num&(1LL<<nbits))?1:0;
printf("%d",k);
if (nbits) printnum(num,nbits-1);
}
void test(void)
{
shift_t l;
l= -1;
printnum(l,NBITS-1);
printf("\n");
l= (1<<(NBITS-2));
printnum(l,NBITS-1);
printf("\n");
l= 5;
printnum(l,NBITS-1);
printf("\n");
}
答案 4 :(得分:0)
如果您不介意分别打印数字,可以使用以下方法:
#include<stdio.h>
#include <stdlib.h>
#include<limits.h>
void bindigit(long long num);
int main()
{
long long number, binaryRepresentation = 0, baseOfOne = 1, remainder;
scanf("%lld", &number);
bindigit(number);
printf("\n");
}
void bindigit(long long num) {
int remainder;
if (num < 2LL) {
printf("%d",(int)num);
} else {
remainder = num % 2;
bindigit(num/2);
printf("%d",remainder);
}
}
答案 5 :(得分:0)
最后,我自己尝试了一个代码,其中包含了您的代码中的创意,
#include<stdio.h>
#include<stdlib.h>
int main() {
unsigned long long number;
int binaryRepresentation[70], remainder, counter, count = 0;
scanf("%llu", &number);
while(number > 0) {
remainder = number % 2;
binaryRepresentation[count++] = remainder;
number = number / 2;
}
for(counter = count-1; counter >= 0; counter--) {
printf("%d", binaryRepresentation[counter]);
}
}