我在C书中读到,对于数组num[7]
,术语num
等同于&num[0]
。这个概念对我来说很好,但是当我写下这个程序时,我再次感到困惑。
#include<stdio.h>
#include<conio.h>
int main()
{
int num[]={21,22,23,24,25,26,27};
int *x,*y,*z;
x=#
y=num;
z=&num[0];
printf("%d %d %d\n",sizeof(x),sizeof(y),sizeof(z));
printf("%d %d %d\n",sizeof(&num),sizeof(num),sizeof(&num[0]));
printf("%d %d %d",*(&num),*(num),*(&num[0]));
getch();
return 0;
}
输出是:
4 4 4
4 28 4
2293536 21 21
如果num
与&num[0]
相同,那么为什么它们的大小会有所不同?什么是第三类术语&num
?我知道它显示了垃圾值,但这种类型的术语是否有意义? z=&num[0]
我已经明白了。编译器显示赋值x=&num
的警告,但对于y=num;
,编译器没有任何问题。如果num
的大小为28
,为什么在没有类型转换的情况下将其分配给整数指针y
?
然后我用这种方式尝试二维数组:
#include<stdio.h>
#include<conio.h>
int main ()
{
int s[4][2]={{1234,56},{1235,57},{1236,58},{1237,59}};
int i
printf ("\n%d %d %d %d %d",sizeof(s[i]),sizeof(&s[i]),sizeof(s),
sizeof(s[0][0]),sizeof(&s));
getch();
return 0;
}
现在输出
8 4 32 4 4
此处sizeof(s[i])
为8
。因为s[i]
是一维数组,它有两个元素,所以很好。但我不清楚术语&s[i]
和&s
的含义。我再次能够看到s
与s[0][0]
不同。我使用Dev C ++ 4.9.9.2版本来运行所有程序。我想明确这三种术语。
答案 0 :(得分:5)
这里有好问题。希望我们都能为您解释这些问题。
鉴于
int num[]={21,22,23,24,25,26,27};
然后
num
具有类型int[]
,因为它是一个声明的整数数组,其内存已分配到位。请注意,它不的类型为int*
,如果您对其进行了malloced,则会出现这种情况。sizeof(num)
是28,因为num
是一个包含7个整数的数组,在您的机器上大小为4个字节。如果int是8个字节,则值为56;如果有2个字节,则值为14,但每个整数最多4个字节。&num[0]
是int*
类型的指针,其值是num
的第一个元素的地址。x
和朋友的大小是4,因为它们被声明为指针,在你的机器上,在你的C编译器下,指针以4个字节分配。要记住的是,当在某些上下文中使用数组时,比如作为参数传递,它将转换为int*
。这就是为什么你可以说*num
并获得21. Tricky,但就是这样。这就是为什么人们通常可以交换num
和&num[0]
,但你真的应该记住这个区别,因为你注意到sizeof
值不同。
转换是y = num
有意义的原因。 y
的类型为int*
,而在C中,您可以自int[]
到int*
进行自动转换。您无法执行x = &num
因为&num
的类型是“指向int数组的指针”。您无法将其分配给int*
(指向int的指针)。
在
的情况下int s [4] [2] = {{1234,56},{1235,57},{1236,58},{1237,59}};
我们将s
的类型设为int[][]
,将&s
的类型设为pointer to int[][]
,将&s[i]
的类型设为int[]
的指针}(因为s[i]
是一个int数组)。由于C允许您为指针分配/传递数组的方式,您可以使用与第一个示例中相同类型的游戏。
您会注意到s
,&s[0]
和&s[0][0]
都指向相同的内存位置,但是,正如您所注意到的,sizeof
值会有所不同。< / p>
答案 1 :(得分:3)
你的矛盾是有效的。 num
等同于&num[0]
的情况不。那简直是假的。数组与指针的类型不同,num
指的是类型为int[7]
的对象,而不是int*
。这就是为什么尺寸不同,例如,因为一个是七个整数的连续集合。
请注意,如果需要,num
可能会转换为int*
,其值为&num[0]
。当然,转换与等价不同。你会发现数组和指针之间的混淆奇怪地突出,因为人们不断重复数组指针的虚假。他们不是。
答案 2 :(得分:3)
现在我的问题是,如果num与&amp; num [0]相同,那么为什么有一个 有多大的差异?
num
是一个数组。 sizeof
对于数组有时会出现令人惊讶的行为,如果你将它传递给一个实际的数组,它会告诉你整个数组的存储大小,但它只告诉你指向数组元素的指针的大小。你传递了这样一个元素的地址。这可能会导致混淆,因为数组名称会降级为函数调用中的指针。
所以,答案是num
与&num[0]
不同 - 后者是num
的第一个元素的地址,包含有关数组总大小的任何信息除去。这两个东西在许多上下文中是可互换的,例如调用实际函数,但不是在调用sizeof
时(它不是函数,而是由编译器处理的特殊关键字)。
答案 3 :(得分:2)
首先,我会尝试向您解释此输出:
4 4 4
4 28 4
2293536 21 21
sizeof()
是c中的一元运算符。编译代码时,它被整数替换,而不是在运行时。因此,编译器会将您的printfs更改为:
printf("%d %d %d\n", 4, 4, 4);
printf("%d %d %d\n", 4, 28, 4);
printf("%d %d %d",*(&num),*(num),*(&num[0]));
在汇编的早期阶段。
在编写sizeof(num)
时,编译器非常友好地为您提供整个数组的大小。这就是定义sizeof如何在数组上工作。除了sizeof(&amp; num)之外,所有其他元素都给出了(int *)的大小,它给出了(int **)的大小(int **与int *的大小相同)。< / p>
关于你的第二个问题;
printf("\n%d %d %d %d %d",sizeof(s[i]),sizeof(&s[i]),sizeof(s),sizeof(s[0][0]),sizeof(&s));
sizeof(s[i]) - size of an array (int[2]) == 8
sizeof(&s[i]) - size of a pointer to an int array sizeof(int **) == 4
sizeof(s) - size of a 2D array containing 8 ints == sizeof(int[8]) == 32
sizeof(s[0][0]) - size of an int === 4
sizeof(&s) - size of a pointer to an array == 4