Tengo un problema para convertir el número de ira doble del tipo entero en binario como el siguiente,

void intToBin(int digit) {
    int b;
    int k = 0;
    char *bits;
    int i;

    bits= (char *) malloc(sizeof(char));
    while (digit) {
        b = digit % 2;
        digit = digit / 2;
        bits[k] = b;
        k++;
    }
    for ( i = k - 1; i >= 0; i--) {
        printf("%d", bits[i]);
    }
}

Pero como puede ver, la entrada de argumentos de esa función es entera.

Me encontré con el error cuando intenté con intToBin(10329216702565230) porque 10329216702565230 está por encima del rango entero.

¿Cómo puedo extender lo que tiene un número entero de doble rango a binario?

Actualizar

He actualizado el siguiente código

void intToBin(uint64_t digit) {
    int b;
    int k = 0;
    char *bits;
    int i;

    bits = malloc(sizeof digit * 64);

    while (digit) {
        b = digit % 2;
        digit = digit / 2;
        bits[k] = b;
        k++;
    }
    for ( i = k - 1; i >= 0; i--) {
        printf("%d", bits[i]);
    }

}

Pero no lo entendí, ¿qué debo hacer para obtener el complemento de 2? m dmnngn

c
0
start01 13 ene. 2018 a las 06:50

3 respuestas

La mejor respuesta

La solución es usar el tipo que admite ese rango de números.

Use unsigned long long o uint64_t (suponiendo que está pasando enteros no negativos, de lo contrario use long long o int64_t). Luego llama a la función así Editado para agregar int64_t a uint64_t del comentario publicado. unsigned long long tiene al menos 64 bits, incluso puede ser más ancho. Con el comentario de OP de obtener una salida de 64 bits, mejor usar (u)int64_t

intToBin(10329216702565230U)

En caso de que quiera usar números negativos, use long long. Llámelo así intToBin(10329216702565230L).

No asignó suficiente memoria: estaba accediendo a la memoria que no ha asignado, lo que resulta en Comportamiento indefinido. Primero asignó 1 char y luego no lo asignó. Puede resolver esto reasignando: reasignar memoria dentro del bucle (reasignar 1 char en un momento dentro del bucle). Y luego úsalo. En lugar de llamar a realloc varias veces, ¿por qué no asigna memoria para 64 char sy luego la usa para almacenar el resultado. Y al final, el espacio sobrante se puede liberar con otra llamada realloc.

No necesita emitir el valor de retorno de malloc (void* a char* la conversión se realiza implícitamente). No comprobaste el valor de retorno de malloc. malloc puede devolver NULL y, en ese caso, debe manejarlo por separado. Por ejemplo:-

   #define NBITS 64
   ...
   ...
   bits = malloc(NBITS);
   if( bits == NULL ){
       perror("malloc failed");
       exit(EXIT_FAILURE);
   }

Nota: El número mágico 64 se presenta con la idea de que unsigned long long es 64 bits al menos. Entonces, durante la conversión, usaremos eso en caso de que el número de bits exceda 64 lo reasignaremos. Una mejor opción es usar lo que chux dijo: sizeof digit * CHAR_BIT.

Además

bits[k] = b+'0';

Estamos poniendo el valor ascii y luego puede imprimirlo así

printf("%c", bits[i]);

Olvidó liberar la memoria asignada. Sin liberarlo (free(bits)), tiene pérdida de memoria.

Comentario de David C. Rankins

4
user2736738 13 ene. 2018 a las 06:02
void intToBin(int digit)
{
int b;
int k = 0;
char *bits;
int i;

bits= (char *) malloc(sizeof(char));
while (digit) {
    b = digit % 2;
    digit = digit / 2;
    bits[k] = b;
    k++;
}
for ( i = k - 1; i >= 0; i--) {
    printf("%d", bits[i]);
}
}

La respuesta es simple,

Reemplace int con int64_t para usar 64 bits en lugar de 32. Por favor, pruébalo y dinos

1
coderredoc 13 ene. 2018 a las 13:11

Reemplace int con int64_t para usar 64 bits en lugar de 32.

0
John Zwinck 13 ene. 2018 a las 05:14