以下哪项是以下程序的正确输出?
如果机器是32位little-endianess并且sizeof(int)是4字节。以下哪项是以下程序的正确输出?
考虑下面的程序:
line1: #include<stdio.h>
line2: {
line3: int arr[3]={2,3,4};
line4: char *p;
line5: p=(char*)arr;
line6: printf("%d",*p);
line7: p=p+1;
line8: printf("%d\n",*p);
line9: return 0;
}
什么是预期的输出?
A
:2 3
B
:2 0
C
:1 0
D
:垃圾值
一件事困扰我的整数指针的浇铸到一个字符指针。
该铸件有多重要?
编译器在第5行做什么? (
p = (char *) arr;
)第7行发生了什么? (
p = p + 1
)如果输出是
20
那么0
是如何打印出来的?
1.重要铸件: - char * p; 这行声明了一个指向字符的指针。这意味着它的属性是可以一次只取消一个字节的 ,并且位移也是一个字节。
p =(char *)arr; 2.类型转换为char *仅用于避免编译器发出警告。 如果你不那么也是同样的行为。
作为指针为一个字符作为我已经写以上P = P + 1个指向下一个字节
-
的printf( “%d \ n”,* P); %d正在将该值格式化为十进制整数,因此十进制格式显示为 ,这里使用* p,并根据其属性可以仅引用一个字节。因此现在内存组织进入画面。 那是你的机器如下小端/ LSB第一或大端/ MSB第一
按你答你的机器跟着小endian.So第一次你答是0 然后下一个字节必须是零,因此输出为0 。 二进制: 2表示为00-00-00-02(字节明智表示) 但在内存中它存储在像第一存储器字节02 02-00-00-00四个字节这样
并在第二个存储器字节00
-
(D)
,或编译器特异性的,因为sizeof(int)
(以及字节顺序)是依赖于平台的。
铸件有多重要?
整体而言,Casting是C语言中不可或缺的一部分(双关语)。
以及在第5行中compilar会做什么?
它将arr
的第一个元素的地址放到p
中。
和行号5之后行号7是怎么回事?
它增加指针,使其指向该内存地址的下一个char
。
如果输出是2 0那么编译器如何打印0?
这是一个结合的恩典和sizeof(int)
。如果没有你机器的规格,我可以做的其他事情就不用解释了。
然而,假设小端和sizeof(int) == 4
,我们可以看到以下内容:
// lets mark these memory regions: |A|B|C|D|
int i = 2; // represented as 0x02000000
char *ptr = (char *) &i; // now ptr points to 0x02 (A)
printf("%d\n", *ptr); // prints '2', because ptr points to 0x02 (A)
ptr++; // increment ptr, ptr now points to 0x00 (B)
printf("%d\n", *ptr); // prints '0', because ptr points to 0x00 (B)
我欣赏你的所有答案,除了最后一个为什么零(0)正在被编译器打印。可能会更加强调 – kTiwari 2012-07-25 15:29:24
@krishnaChandra因为在内存中(小端),“2”表示为“0x0200”,并且第一次打印指针时,结果为“2”(0x02)。当你增加指针时,你会得到下一个字节“0x00”。 – 2012-07-25 15:32:30
(E)上述均不
然而,条件是:(一)你是在一个小端(例如x86)和(b)sizeof(int) >= 2
,这应该打印“20”(两个之间不打印空间)。
a)所述铸造是“必要的”在一个时间,而不是作为一系列int
小号
b键读取阵列的一个字节)这只是强迫所述第一int
的地址转换成指针char
c)按sizeof(char)
递增存储在p
的地址(其为1)
d)的int
的机器表示的第二个字节是由管线8
@EricJ。其实我编译它在我的机器上,并得到2 0作为输出? – kTiwari 2012-07-25 15:27:59
在SPARC或其他big-endian机器上编译它,你应该得到'00' - 这个代码的行为是依赖于平台和编译器的。 – twalberg 2012-07-25 15:31:45
这个问题没有意义,因为无论是endianess还是编译器,也没有提到'sizeof(int)'。 – RedX 2012-07-25 15:32:23