Reputation: 267
I am trying to write a program in C that prints bits of int. for some reason i get wrong values,
void printBits(unsigned int num){
unsigned int size = sizeof(unsigned int);
unsigned int maxPow = 1<<(size*8-1);
printf("MAX POW : %u\n",maxPow);
int i=0,j;
for(;i<size;++i){
for(j=0;j<8;++j){
// print last bit and shift left.
printf("%u ",num&maxPow);
num = num<<1;
}
}
}
My question, first why am i getting this result (for printBits(3)).
MAX POW : 2147483648 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 0 0 2147483648 214748364 8
second is there a better way to do this ?
Upvotes: 16
Views: 113837
Reputation: 158
How about this Macro:
#define print_bits(x) \
do { \
unsigned long long a__ = (x); \
size_t bits__ = sizeof(x) * 8; \
printf(#x ": "); \
while (bits__--) putchar(a__ &(1ULL << bits__) ? '1' : '0'); \
putchar('\n'); \
} while (0)
char c = 3;
int i = -1;
print_bits(c);
print_bits(i);
output:
c: 00000011
i: 11111111111111111111111111111111
This Marco can be used on any primitive datatype and the expression 'x' will be evaluated only once. So you should be safe from side effects.
With the typeof construct you could extend this to structures too:
#define print_bits(x) \
do { \
typeof(x) a__ = (x); \
char *p__ = (char *)&a__ + sizeof(x) - 1; \
size_t bytes__ = sizeof(x); \
printf(#x ": "); \
while (bytes__--) { \
char bits__ = 8; \
while (bits__--) putchar(*p__ & (1 << bits__) ? '1' : '0'); \
p__--; \
} \
putchar('\n'); \
} while (0)
print_bits((struct in_addr){.s_addr = 0xff00ff00});
output:
(struct in_addr){.s_addr = 0xff00ff00}: 11111111000000001111111100000000
Could be useful e.g. in print debugging.
(typeof
is a GNU-extension, use __typeof__
instead if it must work in ISO C programs)
Upvotes: 6
Reputation: 840
// example code `ch7-8.c` from the book `明解C言語 3nd` of Shibata Bouyou
#include<stdio.h>
int count_bits(unsigned x)
{
int bits = 0;
while (x) {
if (x & 1U) bits++;
x >>= 1;
}
return bits;
}
int int_bits(void)
{
return count_bits(~0U);
}
void print_nbits(unsigned x, unsigned n)
{
int i = int_bits();
i = (n < i) ? n - 1 : i - 1;
for (; i >= 0; i--)
putchar(((x >> i) & 1U) ? '1' : '0');
}
int main(void)
{
unsigned i;
for (i = 0; i <= 65535U; i++) {
printf("%5u ", i);
print_nbits(i, 16);
printf(" %06o %04X\n", i, i);
}
return 0;
}
output:
0 0000000000000000 000000 0000
1 0000000000000001 000001 0001
2 0000000000000010 000002 0002
3 0000000000000011 000003 0003
4 0000000000000100 000004 0004
5 0000000000000101 000005 0005
6 0000000000000110 000006 0006
7 0000000000000111 000007 0007
8 0000000000001000 000010 0008
9 0000000000001001 000011 0009
10 0000000000001010 000012 000A
11 0000000000001011 000013 000B
12 0000000000001100 000014 000C
13 0000000000001101 000015 000D
14 0000000000001110 000016 000E
15 0000000000001111 000017 000F
16 0000000000010000 000020 0010
Upvotes: 1
Reputation: 601
I guess You can remove some code and
void printB(unsigned int num){
unsigned int size = sizeof(unsigned int);
int i;
for(i = size*8-1; i>= 0; i--){
printf("%u",(num >>i) & 1 );
}
printf("\n");
}
Upvotes: 1
Reputation: 729
void print_bits(unsigned int x)
{
int i;
for(i=8*sizeof(x)-1; i>=0; i--) {
(x & (1 << i)) ? putchar('1') : putchar('0');
}
printf("\n");
}
Upvotes: 1
Reputation: 93565
To address point two, I'd consider the following, which is simplified a bit for ease of understanding.
void printBits(unsigned int num)
{
for(int bit=0;bit<(sizeof(unsigned int) * 8); bit++)
{
printf("%i ", num & 0x01);
num = num >> 1;
}
}
Upvotes: 12
Reputation: 726659
You are calculating the result correctly, but you are not printing it right. Also you do not need a second loop:
for(;i<size*8;++i){
// print last bit and shift left.
printf("%u ",num&maxPow ? 1 : 0);
num = num<<1;
}
If you'd like to show off, you could replace the conditional with two exclamation points:
printf("%u ", !!(num&maxPow));
Upvotes: 26
Reputation: 183908
The result you get is because num&maxPow
is either 0 or maxPow
. To print 1 instead of maxPow
, you could use printf("%u ", num&maxPow ? 1 : 0);
. An alternative way to print the bits is
while(maxPow){
printf("%u ", num&maxPow ? 1 : 0);
maxPow >>= 1;
}
i.e. shifting the bitmask right instead of num
left. The loop ends when the set bit of the mask gets shifted out.
Upvotes: 10