关于sizeof的问题,请教大家

smilenot 2011-07-04 07:28:31
#include <stdio.h>
static int j;
int fun(int b[100])
{
return sizeof(b);//这个结果为什么不是400呢?
}
struct A
{
};

int main()
{
int a[100];
printf("%d\n",sizeof(a));//a是数组地址,是一个int型的值,结果为4才对呀,我的想法为什么不对呢
printf("%d\n",sizeof(&a));//这个真不懂,不知道&a是表示什么,更不知道sizeof(&a)表示什么
printf("%d",sizeof(A));//空结构体大小为什么为1
return 0;
}
经常对这些东西似懂非懂的,谁能帮我详细说下
...全文
300 26 打赏 收藏 转发到动态 举报
写回复
用AI写文章
26 条回复
切换为时间正序
请发表友善的回复…
发表回复
紫冰 2011-07-18
  • 打赏
  • 举报
回复
更正对int fun(int b[100])的认识:
(1)这种写法是正确的,语法没有问题。只不过C语言对他的处理方式是忽略数组长度100,传入的只是一个指针,即数组首元素的地址。
(2)C99标准增加了对变长数组的支持。使得可以使用变量作为数组的长度。如:
int func(int row ,int column, int ar[row][column])
{
int b[row][column];//用变量定义数组长度
}
冰山上的闪电 2011-07-05
  • 打赏
  • 举报
回复

int main()
{
int a[10];
printf("%d\n",a); //a数组首元素的地址
printf("%d\n",&a);//&a数组的首地址

printf("%d\n", a + 1);
printf("%d\n", &a + 1);


getch();
return 0;
}
a表示数组首元素的地址,&a表示数组的首地址,假设它们为A,虽然它两值是一样的,但是代表的
含义却不相同,请注意a+1 != &a+1,因为a+1是下一个数组元素的地址,所以它应该等于A+sizeof(int),即加上一个数组元素的长度,而&a+1是下一个数组的地址,所以它应该等于A+sizeof(a),即
加上一个数组的长度,虽然此时它已经越界了。。
fcly1981826ly 2011-07-05
  • 打赏
  • 举报
回复
学习,,,
pathuang68 2011-07-05
  • 打赏
  • 举报
回复
[Quote=引用 5 楼 pengzhixi 的回复:]

因为数组传递给函数已经退化为指针了。
[/Quote]

++,这就是正解。

数组作为函数参数传递时,就会退化成指针。
赵4老师 2011-07-05
  • 打赏
  • 举报
回复
VC调试时按Alt+8,TC或BC用TD调试,打开汇编窗口看每句C对应的汇编并单步执行一遍不就啥都明白了吗。
(Linux或Unix下应该也可以在用GDB调试时,看每句C对应的汇编并单步执行。)
想要从本质上理解C指针,必须学习汇编以及C和汇编的对应关系。
从汇编的角度理解和学习C语言的指针,原本看似复杂的东西就会变得非常简单!
指针即地址。“地址又是啥?”“只能从汇编语言和计算机组成原理的角度去解释了。”

提醒:
“学习用汇编语言写程序”

“VC调试时按Alt+8,TC或BC用TD调试,打开汇编窗口看每句C对应的汇编并单步执行一遍。
(Linux或Unix下应该也可以在用GDB调试时,看每句C对应的汇编并单步执行。)
想要从本质上理解C指针,必须学习C和汇编的对应关系。”
不是一回事!
smilenot 2011-07-05
  • 打赏
  • 举报
回复
还有我想知道为什么每次面试的时候都有这样的题目?我不知道这个意义有多大?
AnYidan 2011-07-05
  • 打赏
  • 举报
回复
顶多只能告诉你一个知识点而已,何不静下心了找本书好好看看
the c programming langague
zhaozidong86 2011-07-05
  • 打赏
  • 举报
回复
[Quote=引用 22 楼 qiqisky02 的回复:]

其实很简单,楼主只要区分sizeof()运算对指针和数组的区别就够了。
因为指针是一个地址的值,在现在的系统中一般用32的int来表示,所以
void *p=0;
int a =sizeof(p);则a的值为4。
而sizeof在计算数组和结构体的时候其结果分别为数组和结构体的实际大小。

下面分别解释楼主碰到的具体问题:
(1)函数传递参数
#include <stdio.h>……
[/Quote]
函数定义里面是可以有数组长度的吧,只不过一般不这么用。
smilenot 2011-07-05
  • 打赏
  • 举报
回复
[Quote=引用 22 楼 qiqisky02 的回复:]
其实很简单,楼主只要区分sizeof()运算对指针和数组的区别就够了。
因为指针是一个地址的值,在现在的系统中一般用32的int来表示,所以
void *p=0;
int a =sizeof(p);则a的值为4。
而sizeof在计算数组和结构体的时候其结果分别为数组和结构体的实际大小。

下面分别解释楼主碰到的具体问题:
(1)函数传递参数
#include <stdio.h>
……
[/Quote]
将的非常的详细,非常感谢
ljhhh0123 2011-07-05
  • 打赏
  • 举报
回复
这里只关注标准C,参考《C语言参考手册》第五版。
printf("%d\n",sizeof(a));//a是数组,这是sizeof唯一例外的地方。
printf("%d\n",sizeof(&a));//&a就是数组a的地址。结果为4.
printf("%d",sizeof(A));//结果必须为0,如果不是,就看看那本《深度探索C++对象模型》吧。
紫冰 2011-07-05
  • 打赏
  • 举报
回复
其实很简单,楼主只要区分sizeof()运算对指针和数组的区别就够了。
因为指针是一个地址的值,在现在的系统中一般用32的int来表示,所以
void *p=0;
int a =sizeof(p);则a的值为4。
而sizeof在计算数组和结构体的时候其结果分别为数组和结构体的实际大小。

下面分别解释楼主碰到的具体问题:
(1)函数传递参数
#include <stdio.h>
static int j;
int fun(int b[100])
{
return sizeof(b);//这个结果为什么不是400呢?
}
上面的写法有错误吧,函数定义里面怎么有数组的长度呢?
我猜测你的意思可能是在调用的时候是这样的:
int b[100];
int nsize=fun(b);
而函数定义为:
int fun(int* p)
{
return sizeof(p);//这个结果为什么不是400呢?
}
这样就很明确了,c语言中传递数组参数的时候都是以指针的形式传递的(因为仅传递一个数组名字,函数无法确定其元素个数,因而也无法确定其长度),所以你传递的实参是数组,但在函数体里面则是指针形式,所以fun函数里面计算的sizeof(p)的值当然是4咯。

2、
struct A
{
};

int main()
{
int a[100];
printf("%d\n",sizeof(a));//a是数组地址,是一个int型的值,结果为4才对呀---问题a
printf("%d\n",sizeof(&a));//这个真不懂,不知道&a是表示什么,更不知道sizeof(&a)表示什么--问题b
printf("%d",sizeof(A));//空结构体大小为什么为1---问题c
return 0;
}

a、前面说过,sizeof求数组和结构体的时候表示的是数组和结构体的大小,所以结果应该为400
b、&a的含义学过二维数组就很明白。首先a是数组的首地址,也就是说是一个指针,该值为数组存放在内存中的首地址。&a表示对存放a值的内存单元取地址,结果也是一个指针。总之&a取地址符得到的肯定是一个指针,而sizeof指针的结果就是4
c、这个跟标准的实现有关系。对于空结构体,c语言的实现是默认增加一个char类型的成员,所以其结果为1.
为什么要增加一个char类型的成员呢?这是为了区分该类型不同的实体。
请看下面的例子:
定义A类型变量:
A a1, a2;//如果不增加成员的话,此处则不分配内存
A *p1=&a1;//运行错误,因为a1没有内存。这样与内置类型的使用习惯不符。c/c++推荐自定义的结构体和类与内置类型应当有一致的使用习惯,这样方便使用,且不容易出错。
//而且无法比较俩个指针的是否指向同一目标
A *p2=&a1;
if(p1==p2)
增加一个隐含的成员则可以解决以上矛盾。


个人见解,有不完善的希望大家补充啊。
冰山上的闪电 2011-07-05
  • 打赏
  • 举报
回复
[Quote=引用 20 楼 yanglu252 的回复:]

可以告诉你的是:
printf("%d\n",sizeof(&a));在不同的编译器下面结果是不一样的。VC下面是400,但是GCC下面是4。
其他的嘛都是很基础的,看看书或者找点资料就知道,也是比较好理解的。
[/Quote]
这个应该是4,vc你应该用的是vc6.0,你用vs2008或者vs2010试下
yanglu252 2011-07-05
  • 打赏
  • 举报
回复
可以告诉你的是:
printf("%d\n",sizeof(&a));在不同的编译器下面结果是不一样的。VC下面是400,但是GCC下面是4。
其他的嘛都是很基础的,看看书或者找点资料就知道,也是比较好理解的。
tony2278 2011-07-05
  • 打赏
  • 举报
回复
“当数组当做形参传递后就退化为指针了,所以是4”
序员 2011-07-05
  • 打赏
  • 举报
回复
K&R C里面有
zxl0511 2011-07-04
  • 打赏
  • 举报
回复
[Quote=引用 2 楼 smilenot 的回复:]

引用 1 楼 abao623660072 的回复:
a是数组,&amp;a是数组的地址,a是数组的首地址,一般都不写&amp;的.

这样的话&a的大小就应该是4了,可是VS2005下的结果是400,不解
[/Quote]
sizeof(&a)应该是4,vs2005那个是bug
nightkids_008 2011-07-04
  • 打赏
  • 举报
回复
[Quote=引用 9 楼 bjtbjt 的回复:]
楼主函数传参数都是拷贝
除过了引用。所以你的那个其实只是个指针副本
它指向的是数组的第一个地址而已
这个和数组名不一样的
所以也称退化了的指针
楼主记住
[/Quote]
+++1
5t4rk 2011-07-04
  • 打赏
  • 举报
回复
楼主函数传参数都是拷贝
除过了引用。所以你的那个其实只是个指针副本
它指向的是数组的第一个地址而已
这个和数组名不一样的
所以也称退化了的指针
楼主记住
proghua 2011-07-04
  • 打赏
  • 举报
回复
数组参数转化为指针了
东莞某某某 2011-07-04
  • 打赏
  • 举报
回复
C专家编程 里面好像就是有关于数组名和指针的关系
加载更多回复(6)

69,373

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧