Estoy aprendiendo cómo se representan los números en la memoria. Quiero saber cómo imprimir la representación real (binaria o hexadecimal) en la memoria de algunas variables int y float.
Me gustaría ver qué sucede con esos números cuando sumarlos o restarlos provoca un desbordamiento, por ejemplo.
¿Cómo puedo acceder a la memoria e imprimirla?
utilizar printf() con especificador de acceso %u
–Jaffer Wilson
12 de febrero de 2016 a las 14:34
Si una de las respuestas abordó su pregunta, considere aceptarla.
– dbush
24 de febrero a las 17:26
arbusto
Debería asignar un puntero a la variable en cuestión a un char *y trátelo como una matriz de bytes de longitud sizeof(variable). Luego puede imprimir cada byte en hexadecimal usando el %X especificador de formato para printf.
Puedes definir una función como esta:
void print_bytes(void *ptr, int size)
{
unsigned char *p = ptr;
int i;
for (i=0; i<size; i++) {
printf("%02hhX ", p[i]);
}
printf("\n");
}
Y llámalo así:
int x = 123456;
double y = 3.14;
print_bytes(&x, sizeof(x));
print_bytes(&y, sizeof(y));
Probablemente debería hacer eso unsigned char y use %hhX como especificador de formato.
– Juan Bode
12 de febrero de 2016 a las 15:04
@JohnBode Buena decisión. Editado.
– dbush
12 de febrero de 2016 a las 15:18
@dbush, su ejemplo imprime 40 E2 01 00 (int 123456 -> 32 bits). Creo que debería ser 00 01 E2 40. Esto se debe a que, ¿cómo almacena la memoria los números? ¿O debería modificar el bucle?
– aledruetta
12 de febrero de 2016 a las 15:48
@AleD Esto se debe a la endianidad de su máquina, que es el ordenamiento de bytes de tipos enteros. La mayoría de las máquinas en estos días (como es el caso en este ejemplo) son little-endian, lo que significa que el byte menos significativo es el primero. Si ejecutó esto en una máquina Sun, que es big-endian, vería primero el byte más significativo.
– dbush
12 de febrero de 2016 a las 15:51
chux – Reincorporar a Monica
… para imprimir la representación real (binario …
Para convertir ninguna variable/objeto a una cadena que codifica la forma binaria utiliza una función auxiliar que convierte la memoria en una cadena “binaria”. Este método también maneja punteros de función. Utiliza C99 o posterior.
Salida (Nota: dependiendo del endian-ness, los resultados pueden variar)
Sample
double pi:0100000000001001001000011111101101010100010001000010110100011000
int 42:00000000000000000000000000101010
Este enfoque es fácil de adaptar a la forma hexadecimal.
¡Hola! ¿Puedes explicar el “(char [sizeof(x)*CHAR_BIT + 1]){“”}”? No entiendo por qué hay un “+ 1” y un “{“”}” :/
– Hedwin Bonnavaud
8 sep 2021 a las 11:36
@HedwinBonnavaud ¿Qué tan familiarizado está con literales compuestos? ¿Cuál es el tamaño de memoria necesario para almacenar el cuerda “00001111”? 8 o 9?
– chux – Reincorporar a Monica
8 sep 2021 a las 11:39
lo tengo, agregas +1 para mantener el espacio para almacenar ‘\ 0’ al final, ¿verdad?
– Hedwin Bonnavaud
8 sep 2021 a las 13:10
@HedwinBonnavaud Sí +1 para el carácter nulo.
– chux – Reincorporar a Monica
8 sep 2021 a las 13:39
ok gracias por este agradable y útil código por cierto
– Hedwin Bonnavaud
8 sep 2021 a las 13:50
Digamos que tiene una variable int llamada memoria. Asegúrese de ver cuántos bits tiene; para muchos procesadores, un int es de 32 bits, así como una dirección de memoria. Así que necesitas recorrer cada bit, así:
unsigned int memory = 1234;
for (int i = 0; i < 32; i++)
{
printf("%d ", memory >> i & 1);
}
Este método simple combina cada bit con 1 y cambia cada bit por 1.
mejor usando el ciclo while con memoria con cociente, recordatorio para evitar problemas con los bits del procesador.
– Yoon-Geun Kwon
12/02/2016 a las 14:35
@Yoon-GeunKwon: el cambio no depende del orden de bytes o bits. Se define matemáticamente (división/multiplicación por 2 a la n) según el proyecto de norma C11 6.5.7 Bitwise shift operators.
– FEO
12 de febrero de 2016 a las 14:45
Esto supone un int de 32 bits, lo que puede no ser cierto
Llamada print_bits(memory address of variable, size of variable in byte).
void print_bits(void *ptr, int size) //ptr = memory address of variable, size = size of variable in byte
{
long long *ch = ptr;
int size_bits = size * 8;
for(int i = size_bits-1; i>=0; i--){
printf("%lld", *ch >> i & 1) ;
}
}
Ha sido probado con éxito, trabajando con cualquier variable menor o igual a 64 bits. Esto probablemente funcionará correctamente con variables de otros tamaños (no probado).
Vocación:
double d = -7.92282286274e+28;
print_bits(&d, sizeof(d));
Esta web utiliza cookies propias y de terceros para su correcto funcionamiento y para fines analíticos y para mostrarte publicidad relacionada con sus preferencias en base a un perfil elaborado a partir de tus hábitos de navegación. Al hacer clic en el botón Aceptar, acepta el uso de estas tecnologías y el procesamiento de tus datos para estos propósitos.
Configurar y más información
utilizar
printf()
con especificador de acceso%u
–Jaffer Wilson
12 de febrero de 2016 a las 14:34
Si una de las respuestas abordó su pregunta, considere aceptarla.
– dbush
24 de febrero a las 17:26