pigsploof
pigsploof

Reputation: 35

Printing a long in binary 64-bit representation

I'm trying to print the binary representation of a long in order to practice bit manipulation and setting various bits in the long for a project I am working on. I successfully can print the bits on ints but whenever I try to print 64 bits of a long the output is screwy. Here is my code:

#include <stdio.h> 

void printbits(unsigned long n){
    unsigned long i; 
    i = 1<<(sizeof(n)*4-1);
    while(i>0){
         if(n&1)
              printf("1"); 
         else 
              printf("0"); 
         i >>= 1; 
}

int main(){
    unsigned long n=10; 
    printbits(n); 
    printf("\n"); 
}

My output is 0000000000000000000000000000111111111111111111111111111111111110. Thanks for help!

Upvotes: 1

Views: 3053

Answers (3)

CoffeeTableEspresso
CoffeeTableEspresso

Reputation: 2652

The following should do what you want:

#include <stdio.h>

void printbits(unsigned long number, unsigned int num_bits_to_print)
{
    if (number || num_bits_to_print > 0) {
        printbits(number >> 1, num_bits_to_print - 1);
        printf("%d", number & 1);
    }
}

We keep calling the function recursively until either we've printed enough bits, or we've printed the whole number, whichever takes more bits.

wrapping this in another function directly does exactly what you want:

void printbits64(unsigned long number) {
    printbits(number, 64);
}

Upvotes: 0

Kon
Kon

Reputation: 4099

The problem is that i = 1<<(sizeof(n)*4-1) is not correct for a number of reasons.

  1. sizeof(n)*4 is 32, not 64. you probably want sizeof(n)*8
  2. 1<<63 may give you overflow because 1 may be 32-bits by default. You should use 1ULL<<(sizeof(n)*8-1)
  3. unsigned long is not necessarily 64 bits. You should use unsigned long long

If you want to be extra thorough, use sizeof(n) * CHAR_BIT (defined in <limits.h>).

In general, you should use stdint defines (e.g. uint64_t) whenever possible.

Upvotes: 2

Ry-
Ry-

Reputation: 224962

  • 4 isn’t the right number of bits in a byte
  • Even though you’re assigning it to an unsigned long, 1 << … is an int, so you need 1UL
  • n&1 should be n&i
  • There’s a missing closing brace

Fixes only:

#include <limits.h>
#include <stdio.h> 

void printbits(unsigned long n){
    unsigned long i; 
    i = 1UL<<(sizeof(n)*CHAR_BIT-1);
    while(i>0){
         if(n&i)
              printf("1"); 
         else 
              printf("0"); 
         i >>= 1;
    }
}

int main(){
    unsigned long n=10; 
    printbits(n); 
    printf("\n"); 
}

And if you want to print a 64-bit number specifically, I would hard-code 64 and use uint_least64_t.

Upvotes: 4

Related Questions