实验代码之show-bytes.c

    xiaoxiao2025-03-21  49

    本章实验代码是为了解int、float以及指针类型的字节大小。并且通过对数值12345678与87654321的对比让大家能够了解到自己机器的大端小端存储方式。

    /* show-bytes - prints byte representation of data */ /* $begin show-bytes */ #include <stdio.h> /* $end show-bytes */ #include <stdlib.h> #include <string.h> /* $begin show-bytes */ typedef unsigned char *byte_pointer; //typedef char *byte_pointer; //typedef int *byte_pointer; void show_bytes(byte_pointer start, size_t len) { size_t i; for (i = 0; i < len; i++) printf("%p\t0x%.2x\n", &start[i], start[i]); printf("\n"); } void show_int(int x) { show_bytes((byte_pointer) &x, sizeof(int)); } void show_float(float x) { show_bytes((byte_pointer) &x, sizeof(float)); } void show_pointer(void *x) { show_bytes((byte_pointer) &x, sizeof(void *)); } /* $end show-bytes */ /* $begin test-show-bytes */ void test_show_bytes(int val) { int ival = val; //float fval = (float) ival; //double fval = (double) ival; double fval = 1; int *pval = &ival; printf("Stack variable ival = %d\n", ival); printf("(int)ival:\n"); show_int(ival); printf("(float)ival:\n"); show_float(fval); printf("&ival:\n"); show_pointer(pval); } /* $end test-show-bytes */ void simple_show_a() { /* $begin simple-show-a */ int val = 0x87654321; byte_pointer valp = (byte_pointer) &val; show_bytes(valp, 1); /* A. */ show_bytes(valp, 2); /* B. */ show_bytes(valp, 3); /* C. */ /* $end simple-show-a */ } void simple_show_b() { /* $begin simple-show-b */ int val = 0x12345678; byte_pointer valp = (byte_pointer) &val; show_bytes(valp, 1); /* A. */ show_bytes(valp, 2); /* B. */ show_bytes(valp, 3); /* C. */ /* $end simple-show-b */ } void float_eg() { int x = 3490593; float f = (float) x; printf("For x = %d\n", x); show_int(x); show_float(f); x = 3510593; f = (float) x; printf("For x = %d\n", x); show_int(x); show_float(f); } void string_ueg() { /* $begin show-ustring */ const char *s = "ABCDEF"; show_bytes((byte_pointer) s, strlen(s)); /* $end show-ustring */ } void string_leg() { /* $begin show-lstring */ const char *s = "abcdef"; show_bytes((byte_pointer) s, strlen(s)); /* $end show-lstring */ } void show_twocomp() { /* $begin show-twocomp */ short x = 12345; short mx = -x; show_bytes((byte_pointer) &x, sizeof(short)); show_bytes((byte_pointer) &mx, sizeof(short)); /* $end show-twocomp */ } int main(int argc, char *argv[]) { int val = 12345; if (argc > 1) { val = strtol(argv[1], NULL, 0); printf("calling test_show_bytes\n"); test_show_bytes(val); } else { printf("calling show_twocomp\n"); show_twocomp(); printf("Calling simple_show_a\n"); simple_show_a(); printf("Calling simple_show_b\n"); simple_show_b(); printf("Calling float_eg\n"); float_eg(); printf("Calling string_ueg\n"); string_ueg(); printf("Calling string_leg\n"); string_leg(); } return 0; }

    1.不带参数时运行结果如下(typedef unsigned char *byte_pointer时):

    /*1.不带参数的运行结果 calling show_twocomp 0x7ffecafe81f4 0x39 0x7ffecafe81f5 0x30 0x7ffecafe81f6 0xc7 0x7ffecafe81f7 0xcf Calling simple_show_a 0x7ffecafe81ec 0x21 0x7ffecafe81ec 0x21 0x7ffecafe81ed 0x43 0x7ffecafe81ec 0x21 0x7ffecafe81ed 0x43 0x7ffecafe81ee 0x65 Calling simple_show_b 0x7ffecafe81ec 0x78 0x7ffecafe81ec 0x78 0x7ffecafe81ed 0x56 0x7ffecafe81ec 0x78 0x7ffecafe81ed 0x56 0x7ffecafe81ee 0x34 Calling float_eg For x = 3490593 0x7ffecafe81cc 0x21 0x7ffecafe81cd 0x43 0x7ffecafe81ce 0x35 0x7ffecafe81cf 0x00 0x7ffecafe81cc 0x84 0x7ffecafe81cd 0x0c 0x7ffecafe81ce 0x55 0x7ffecafe81cf 0x4a For x = 3510593 0x7ffecafe81cc 0x41 0x7ffecafe81cd 0x91 0x7ffecafe81ce 0x35 0x7ffecafe81cf 0x00 0x7ffecafe81cc 0x04 0x7ffecafe81cd 0x45 0x7ffecafe81ce 0x56 0x7ffecafe81cf 0x4a Calling string_ueg 0x55b808493d34 0x41 0x55b808493d35 0x42 0x55b808493d36 0x43 0x55b808493d37 0x44 0x55b808493d38 0x45 0x55b808493d39 0x46 Calling string_leg 0x55b808493d3b 0x61 0x55b808493d3c 0x62 0x55b808493d3d 0x63 0x55b808493d3e 0x64 0x55b808493d3f 0x65 0x55b808493d40 0x66

    不带参数时会进行示例eg代码部分,此部分主要是对比float型及char指针型的数据进行字节测试;在show_a和show_b部分对机器内部存储方式进行了测试,据测试可知,本机为小端模式,如show_a中87654321则将低位字节21保存在低地址0x7ffecafe81ec中。

    2.x=3000时,结果如下:

    2.x=3000 calling test_show_bytes Stack variable ival = 3000 (int)ival: 0x7fff3275689c 0xb8 0x7fff3275689d 0x0b 0x7fff3275689e 0x00 0x7fff3275689f 0x00 (float)ival: 0x7fff3275689c 0x00 0x7fff3275689d 0x80 0x7fff3275689e 0x3b 0x7fff3275689f 0x45 &ival: 0x7fff32756898 0xc4 0x7fff32756899 0x68 0x7fff3275689a 0x75 0x7fff3275689b 0x32 0x7fff3275689c 0xff 0x7fff3275689d 0x7f 0x7fff3275689e 0x00 0x7fff3275689f 0x00

    此时代码测试内容为输入值3000的int、float以及指针型字节大小测试,由上可知int型占4个字节,float型4个字节,而指针类型占8个字节,注意,最后一段是指针所在地址而不是指针内容值!

    3.x=-10000时,结果如下:

    3.x=-10000 calling test_show_bytes Stack variable ival = -10000 (int)ival: 0x7ffe23b829cc 0xf0 0x7ffe23b829cd 0xd8 0x7ffe23b829ce 0xff 0x7ffe23b829cf 0xff (float)ival: 0x7ffe23b829cc 0x00 0x7ffe23b829cd 0x40 0x7ffe23b829ce 0x1c 0x7ffe23b829cf 0xc6 &ival: 0x7ffe23b829c8 0xf4 0x7ffe23b829c9 0x29 0x7ffe23b829ca 0xb8 0x7ffe23b829cb 0x23 0x7ffe23b829cc 0xfe 0x7ffe23b829cd 0x7f 0x7ffe23b829ce 0x00 0x7ffe23b829cf 0x00

    该部分测试输入值为-10000,知负数与正数在字节大小上并无区别,。

    4.x=3.14时,结果如下:

    4.x=3.14 calling test_show_bytes Stack variable ival = 3 (int)ival: 0x7ffe65fef77c 0x03 0x7ffe65fef77d 0x00 0x7ffe65fef77e 0x00 0x7ffe65fef77f 0x00 (float)ival: 0x7ffe65fef77c 0x00 0x7ffe65fef77d 0x00 0x7ffe65fef77e 0x40 0x7ffe65fef77f 0x40 &ival: 0x7ffe65fef778 0xa4 0x7ffe65fef779 0xf7 0x7ffe65fef77a 0xfe 0x7ffe65fef77b 0x65 0x7ffe65fef77c 0xfe 0x7ffe65fef77d 0x7f 0x7ffe65fef77e 0x00 0x7ffe65fef77f 0x00

    当输入端为3.14时,因为最初的输入定义是int型,所以最开始在赋值时便将输入值舍为3,其余部分并无区别。

    当我们将unsigned char型指针换成char型、int型指针时

    typedef unsigned char *byte_pointer; //typedef char *byte_pointer; //typedef int *byte_pointer;

    char型x=-10000时:

    calling test_show_bytes Stack variable ival = -10000 (int)ival: 0x7ffcb8dd92fc 0xfffffff0 0x7ffcb8dd92fd 0xffffffd8 0x7ffcb8dd92fe 0xffffffff 0x7ffcb8dd92ff 0xffffffff (float)ival: 0x7ffcb8dd92fc 0x00 0x7ffcb8dd92fd 0x40 0x7ffcb8dd92fe 0x1c 0x7ffcb8dd92ff 0xffffffc6 &ival: 0x7ffcb8dd92f8 0x24 0x7ffcb8dd92f9 0xffffff93 0x7ffcb8dd92fa 0xffffffdd 0x7ffcb8dd92fb 0xffffffb8 0x7ffcb8dd92fc 0xfffffffc 0x7ffcb8dd92fd 0x7f 0x7ffcb8dd92fe 0x00 0x7ffcb8dd92ff 0x00

    取负值时会自动向前扩充符号位,所以出现8位十六进制。下同。

    int型x=-10000时:

    calling test_show_bytes Stack variable ival = -10000 (int)ival: 0x7ffd538ba42c 0xffffd8f0 0x7ffd538ba430 0x538ba470 0x7ffd538ba434 0x7ffd 0x7ffd538ba438 0xa843a90e (float)ival: 0x7ffd538ba42c 0xc61c4000 0x7ffd538ba430 0x538ba470 0x7ffd538ba434 0x7ffd 0x7ffd538ba438 0xa843a924 &ival: 0x7ffd538ba428 0x538ba454 0x7ffd538ba42c 0x7ffd 0x7ffd538ba430 0x538ba470 0x7ffd538ba434 0x7ffd 0x7ffd538ba438 0xa843a93c 0x7ffd538ba43c 0x5606 0x7ffd538ba440 0xa843ad52 0x7ffd538ba444 0x5606
    最新回复(0)