由买买提看人间百态

boards

本页内容为未名空间相应帖子的节选和存档,一周内的贴子最多显示50字,超过一周显示500字 访问原贴
Programming版 - C一个问题搞不懂
相关主题
JHQ的一道指针题。再问C++问题。
简单的c code问题this和&*this的区别
问个指针array 的简单问题c ptr question
谁给解释一下这个c question请教两道linux面试题目
array和pointer在作为函数返回时有啥区别 (C)不如各位高手挑个专题讲讲C++11吧
int *a [] 和int (*a)[] 一样吗请教一道C语言的题目
C 语言,初学者问题(4),读取字符指针内容Linux下有办法通过C/C++得到已经调入内存的library的full path么
dereference a NULL pointer in C数组问题
相关话题的讨论汇总
话题: multi话题: array话题: printf话题: pn
进入Programming版参与讨论
1 (共1页)
m*********a
发帖数: 3299
1
二位矩阵array,比如multi[5][10]
为啥multi,*multi,&multi的地址都是一样的?
看下面的程序的运行结果
&multi is 0028FE58
multi is 0028FE58
*multi is 0028FE58
**multi is 67
&multi[0] is 0028FE58
multi[0] is 0028FE58
&multi[0][0] is 0028FE58
multi[0][0] is 67
#include
int main(void){
int multi[5][10]; /*define a two dimensional 5x10 array with a name multi*/
multi[0][0]=67; /*assign 67 to the first element of array*/
printf("&multi is %pn",&multi);
printf("multi is %pn",multi);
printf("*multi is %pn",*multi);
printf("**multi is %dn",**multi);
printf("&multi[0] is %pn",&multi[0]);
printf("multi[0] is %pn",multi[0]);
printf("&multi[0][0] is %pn",&multi[0][0]);
printf("multi[0][0] is %dn",multi[0][0]);
return 0;
}
d****i
发帖数: 4809
2
This can be a bit confusing. In C, multi-dimensional array is stored in
contiguous memory. So c[i][j]=*(*(c+i)+j). For each line, see my comment
below:
#include
int main(void){
int multi[5][10]; /*define a two dimensional 5x10 array with a name multi*/
multi[0][0]=67; /*assign 67 to the first element of array*/
printf("&multi is %pn",&multi); //address of the array
printf("multi is %pn",multi); //same as above
printf("*multi is %pn",*multi); //address of the first row of the array,
which is the same as the address of the array
printf("**multi is %dn",**multi); //the first element
printf("&multi[0] is %pn",&multi[0]); //the address of the first row,
which is the same as multi
printf("multi[0] is %pn",multi[0]); //same as above
printf("&multi[0][0] is %pn",&multi[0][0]); //The address of the first
element, which is the same as address of the array
printf("multi[0][0] is %dn",multi[0][0]); //first element
return 0;
}

【在 m*********a 的大作中提到】
: 二位矩阵array,比如multi[5][10]
: 为啥multi,*multi,&multi的地址都是一样的?
: 看下面的程序的运行结果
: &multi is 0028FE58
: multi is 0028FE58
: *multi is 0028FE58
: **multi is 67
: &multi[0] is 0028FE58
: multi[0] is 0028FE58
: &multi[0][0] is 0028FE58

m*********a
发帖数: 3299
3
多谢回答
你知道这个问题的答案吗?
比如需要二次deference **multi才会给出67
但是如果你定义一个指针 int *ptr;
ptr=multi;
*ptr就等于67了

,

【在 d****i 的大作中提到】
: This can be a bit confusing. In C, multi-dimensional array is stored in
: contiguous memory. So c[i][j]=*(*(c+i)+j). For each line, see my comment
: below:
: #include
: int main(void){
: int multi[5][10]; /*define a two dimensional 5x10 array with a name multi*/
: multi[0][0]=67; /*assign 67 to the first element of array*/
: printf("&multi is %pn",&multi); //address of the array
: printf("multi is %pn",multi); //same as above
: printf("*multi is %pn",*multi); //address of the first row of the array,

S*A
发帖数: 7142
4

这个说法其实要是不懂 C array 指针的地址退化规则理解会更加混乱。
看了你的解释事乎访问 c[i][j] 要 de-reference 变量 c 两次。
其实没有。这里只有一个 load.
c[i][j] 等价于 *(base_addr + i*ARRAY_SIZE(c[0]) + j), 其中 ARRAY_SIZE
是 constant. base_addr 是数组 C 的地址。
,

【在 d****i 的大作中提到】
: This can be a bit confusing. In C, multi-dimensional array is stored in
: contiguous memory. So c[i][j]=*(*(c+i)+j). For each line, see my comment
: below:
: #include
: int main(void){
: int multi[5][10]; /*define a two dimensional 5x10 array with a name multi*/
: multi[0][0]=67; /*assign 67 to the first element of array*/
: printf("&multi is %pn",&multi); //address of the array
: printf("multi is %pn",multi); //same as above
: printf("*multi is %pn",*multi); //address of the first row of the array,

S*A
发帖数: 7142
5
你需要知道,& 取地址是有特例的, 那就是数组和函数指针。
数组一般的表达为 a[sub_script]. 函数是 func(..)
如果没有后面的 【】 ,数组自动退化为数组的指针。
a 是 &a[0] 的简化写法, 这是一个隐含规则,当 a 后面没有【】的
时候触发。
*multi = multi[0] ,这是一个一维数组。Type 是 basetype[len_of_y]
所以 **multi = *(multi【0】)=multi【0】【0】

【在 m*********a 的大作中提到】
: 多谢回答
: 你知道这个问题的答案吗?
: 比如需要二次deference **multi才会给出67
: 但是如果你定义一个指针 int *ptr;
: ptr=multi;
: *ptr就等于67了
:
: ,

S*A
发帖数: 7142
6
你这个例子里面区别是退化后的 C type
ptr 的 C type 是 int *
mutli 的 C type 是 int [][]
multi[0] 的 C type 是 int 【】,等价于 int *。

【在 m*********a 的大作中提到】
: 多谢回答
: 你知道这个问题的答案吗?
: 比如需要二次deference **multi才会给出67
: 但是如果你定义一个指针 int *ptr;
: ptr=multi;
: *ptr就等于67了
:
: ,

z*******n
发帖数: 1034
7
不是memory order的问题 是arrays 和 pointers的区别问题

,

【在 d****i 的大作中提到】
: This can be a bit confusing. In C, multi-dimensional array is stored in
: contiguous memory. So c[i][j]=*(*(c+i)+j). For each line, see my comment
: below:
: #include
: int main(void){
: int multi[5][10]; /*define a two dimensional 5x10 array with a name multi*/
: multi[0][0]=67; /*assign 67 to the first element of array*/
: printf("&multi is %pn",&multi); //address of the array
: printf("multi is %pn",multi); //same as above
: printf("*multi is %pn",*multi); //address of the first row of the array,

t****t
发帖数: 6806
8
actually, array is NOT equivalent to pointer. array will decay to pointer wh
en use in expression, with certain exceptions.

【在 S*A 的大作中提到】
: 你这个例子里面区别是退化后的 C type
: ptr 的 C type 是 int *
: mutli 的 C type 是 int [][]
: multi[0] 的 C type 是 int 【】,等价于 int *。

z*******n
发帖数: 1034
9
英语的好处就是术语 中文有时候你不知道在说什么 cfaq是不是就好理解的解释

wh

【在 t****t 的大作中提到】
: actually, array is NOT equivalent to pointer. array will decay to pointer wh
: en use in expression, with certain exceptions.

S*A
发帖数: 7142
10
对,这是比较正式的一点说法。
我是想说他的区别关键在 C type 上面的结果。
你说说 array in expression 还有什么特别 exceptions?
前面有 &, sizeof (array), typeof(array)?
array 到了编译器后端就全部变成 pointer 统一起来
了。这 array vs pointer 对生成代码没有什么区别。

wh

【在 t****t 的大作中提到】
: actually, array is NOT equivalent to pointer. array will decay to pointer wh
: en use in expression, with certain exceptions.

相关主题
int *a [] 和int (*a)[] 一样吗再问C++问题。
C 语言,初学者问题(4),读取字符指针内容this和&*this的区别
dereference a NULL pointer in Cc ptr question
进入Programming版参与讨论
m*********a
发帖数: 3299
11
讨论这么热烈。我还是只能说array不是指针来理解。
他有自己的规则, **multi对于array不是deference二次
但是对于指针**ptr就是,deference二次。
是不?

wh

【在 t****t 的大作中提到】
: actually, array is NOT equivalent to pointer. array will decay to pointer wh
: en use in expression, with certain exceptions.

d****i
发帖数: 4809
12
对,你这个解释更好,我那个等于实际上是对于指向指针的指针来说的,实际上对于
array来说只有derefenrece一次。

【在 S*A 的大作中提到】
: 对,这是比较正式的一点说法。
: 我是想说他的区别关键在 C type 上面的结果。
: 你说说 array in expression 还有什么特别 exceptions?
: 前面有 &, sizeof (array), typeof(array)?
: array 到了编译器后端就全部变成 pointer 统一起来
: 了。这 array vs pointer 对生成代码没有什么区别。
:
: wh

z*******n
发帖数: 1034
13
哪个编译器

【在 S*A 的大作中提到】
: 对,这是比较正式的一点说法。
: 我是想说他的区别关键在 C type 上面的结果。
: 你说说 array in expression 还有什么特别 exceptions?
: 前面有 &, sizeof (array), typeof(array)?
: array 到了编译器后端就全部变成 pointer 统一起来
: 了。这 array vs pointer 对生成代码没有什么区别。
:
: wh

m*********a
发帖数: 3299
14
c[i][j] 等价于 *(base_addr + i*ARRAY_SIZE(c[0]) + j),这个是对的
这个base_addr 是 *multi 或 multi[0],不是multi

【在 d****i 的大作中提到】
: 对,你这个解释更好,我那个等于实际上是对于指向指针的指针来说的,实际上对于
: array来说只有derefenrece一次。

t****t
发帖数: 6806
15
"The exceptions are when the array is the operand of a sizeof or & operator,
or is a string literal initializer for a character array."
C FAQ

【在 S*A 的大作中提到】
: 对,这是比较正式的一点说法。
: 我是想说他的区别关键在 C type 上面的结果。
: 你说说 array in expression 还有什么特别 exceptions?
: 前面有 &, sizeof (array), typeof(array)?
: array 到了编译器后端就全部变成 pointer 统一起来
: 了。这 array vs pointer 对生成代码没有什么区别。
:
: wh

S*A
发帖数: 7142
16
嗯,和我想的差不多。我漏掉了 literal string initializer
FAQ 漏掉了 typeof。

operator,

【在 t****t 的大作中提到】
: "The exceptions are when the array is the operand of a sizeof or & operator,
: or is a string literal initializer for a character array."
: C FAQ

t****t
发帖数: 6806
17
typeof is not part of standard C.

【在 S*A 的大作中提到】
: 嗯,和我想的差不多。我漏掉了 literal string initializer
: FAQ 漏掉了 typeof。
:
: operator,

f*******n
发帖数: 12623
18
关于 **multi,是multi(int[5][10]),decay成指针(int (*)[10]),跟着
dereference(结果int[10]),再decay成指针(int *),跟着再dereference(结果
int)。所以**multi的确是有两次dereference,只不过再加上两次decay。

【在 m*********a 的大作中提到】
: 讨论这么热烈。我还是只能说array不是指针来理解。
: 他有自己的规则, **multi对于array不是deference二次
: 但是对于指针**ptr就是,deference二次。
: 是不?
:
: wh

S*A
发帖数: 7142
19
你这个理解不对。只有一次 dereference。
二维的下标只是用来计算转换的连续一维数组(内存)的 offset。
下标的 offset 计算本身不是 dereference.
我给你这个示范程序,注意看这里面的 array assign.
只用了一个 dereference。
======================
int a[5][6];
void foo(void)
{
a[1][2] = 1;
**a = 2;
}
======================
$ gcc -S -O2 multi.c
.file "multi.c"
.text
.p2align 4,,15
.globl foo
.type foo, @function
foo:
.LFB0:
.cfi_startproc
movl $1, a+32(%rip) // 这里是 a[1][2] = 1
movl $2, a(%rip) // 这里是 **a = 2
ret
.cfi_endproc
.LFE0:
.size foo, .-foo
.comm a,120,32
.ident "GCC: (GNU) 4.8.2 20131212 (Red Hat 4.8.2-7)"
.section .note.GNU-stack,"",@progbits

【在 f*******n 的大作中提到】
: 关于 **multi,是multi(int[5][10]),decay成指针(int (*)[10]),跟着
: dereference(结果int[10]),再decay成指针(int *),跟着再dereference(结果
: int)。所以**multi的确是有两次dereference,只不过再加上两次decay。

f*******n
发帖数: 12623
20
我的理解完全对。我是说语义。跟compiler怎么实现没有关系。

【在 S*A 的大作中提到】
: 你这个理解不对。只有一次 dereference。
: 二维的下标只是用来计算转换的连续一维数组(内存)的 offset。
: 下标的 offset 计算本身不是 dereference.
: 我给你这个示范程序,注意看这里面的 array assign.
: 只用了一个 dereference。
: ======================
: int a[5][6];
: void foo(void)
: {
: a[1][2] = 1;

相关主题
请教两道linux面试题目Linux下有办法通过C/C++得到已经调入内存的library的full path么
不如各位高手挑个专题讲讲C++11吧数组问题
请教一道C语言的题目Linux GNU C, readlink问题
进入Programming版参与讨论
S*A
发帖数: 7142
21
Dereference means accessing the memory variable by the pointer
address. In other words, dereference meaning memory load or
store using pointer.
int multi[4][5];
multi【0】 as expression can decay to a pointer. That itself
is not an deference. Just like
int array[5];
expression "array" by itself is not a dereference.
It is just a pointer.

【在 f*******n 的大作中提到】
: 我的理解完全对。我是说语义。跟compiler怎么实现没有关系。
f*******n
发帖数: 12623
22
No. Dereference means the * operator, which takes a "pointer to T"
expression and evaluates to a "T" expression.
And arrays and pointers are very different things.

【在 S*A 的大作中提到】
: Dereference means accessing the memory variable by the pointer
: address. In other words, dereference meaning memory load or
: store using pointer.
: int multi[4][5];
: multi【0】 as expression can decay to a pointer. That itself
: is not an deference. Just like
: int array[5];
: expression "array" by itself is not a dereference.
: It is just a pointer.

S*A
发帖数: 7142
23
Where is your definition come from? Any link?
The stander C definition does not have definition for "dereference".
The closest one I can find about the memory reference is at:
http://cplus.about.com/od/glossar1/g/dereference.htm
You said array and pointer are very different thing.
At the same time you are using pointer operation to explain
array dereference.

【在 f*******n 的大作中提到】
: No. Dereference means the * operator, which takes a "pointer to T"
: expression and evaluates to a "T" expression.
: And arrays and pointers are very different things.

1 (共1页)
进入Programming版参与讨论
相关主题
数组问题array和pointer在作为函数返回时有啥区别 (C)
Linux GNU C, readlink问题int *a [] 和int (*a)[] 一样吗
怎么得到char *分配空间的大小?C 语言,初学者问题(4),读取字符指针内容
cpp指针地址是virtual memory address还是physical address?dereference a NULL pointer in C
JHQ的一道指针题。再问C++问题。
简单的c code问题this和&*this的区别
问个指针array 的简单问题c ptr question
谁给解释一下这个c question请教两道linux面试题目
相关话题的讨论汇总
话题: multi话题: array话题: printf话题: pn