Error[8]: Undefined offset: 912, File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 121
File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 473, decode(

指针的进阶(4)- 数组的练习 sizeof 和 strlen


前言

前面已经介绍了数组和指针的知识点,并且用类比方法做了总结。先简要复习与本文练习相关的知识点:

要学以致用,才能更加深入的理解所学的知识点,因此本文主要是数组和指针相关知识点的练习:


1、 相关知识点复习

在前面的学习中,我们经常碰到数组名、sizeof、strlen,本文的练习也会用到它们,先对这些知识点进行复习。

1.1 复习数组名

前面在 【C语言基础5——数组(1)】4.2 和4.3小结 中已经初步学习过了数组名的知识点。

在进阶中更深入的学习了数组和指针后,对数组名理解更加深刻了,温故而知新,首先还是复习下数组名的知识点:

但是有两个例外:

1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
type_t arr_name [const_n];
type_t 是指数组的元素类型
const_n 是一个常量表达式,用来指定数组的大小

学完指针后,对 [ ] 有了更加深刻的理解,将 *** 作符[ ]和取地址 &、定义指针符号 *结合:

1.2.1 一维数组中三者的联系

1.2.2 二维数组中三者的联系


二维数组举例,对照上图和下面的代码分析,可见二维数组的知识点其实是很密集的:

int main()
{
	int a[2][3] = { {1,2,3},{4,5,6 } };
	return 0;
}

注意各个监视对象的类型,类型不一样代表的意义不一样:

1.3 复习sizeof

sizeof 是一个 *** 作符,sizeof 计算的是对象所占内存的大小-单位是字节,不在乎内存中存放的是什么,只在乎内存大小

1.4 复习strlen

strlen 是一个库函数,功能:求字符串长度,从给定的地址向后访问字符,统计\0之前出现的字符个数。

2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
int a[] = { 1,2,3,4 };
	printf("%d\n", sizeof(a));//sizeof(数组名),求取的是整个数组的大小 16
	printf("%d\n", sizeof(a + 0));//数组名不是单独使用,a+0表示首元素的地址,地址的大小就是 4/8
	printf("%d\n", sizeof(*a));//a表示首元素的地址,*a表示数组的首元素,求第一个元素的大小 4
	printf("%d\n", sizeof(a + 1));//a表示首元素的地址,a+1表示第二个元素的地址,求大小 4/8
	printf("%d\n", sizeof(a[1]));//a[1]表示数组第二个元素,求大小 4
	printf("%d\n", sizeof(&a));//&a表示整个数组的地址,求大小 4/8
	printf("%d\n", sizeof(*&a));//*&a 对整个数组的地址解引用,拿到整个数组,求大小 16
	printf("%d\n", sizeof(&a + 1));//&a+1表示跳过一个数组后的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0]));//&a[0]首元素的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0] + 1));//&a[0]+1数组第二个元素的地址,求大小 4/8

3、一维字符数组 3.1 sizeof 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };
	printf("%d\n", sizeof(arr));//sizeod(数组名),所占内存大小。6个字符 ,求大小 6
	printf("%d\n", sizeof(arr + 0));//arr表示首元素的地址,arr+0表示首元素的地址,地址求大小 4/8
	printf("%d\n", sizeof(*arr));//arr表示首元素的地址,*arr取得首元素是一个字符,求大小 1
	printf("%d\n", sizeof(arr[1]));//arr[1]表示第二个元素,是一个字符,求大小 1
	printf("%d\n", sizeof(&arr));//&arr取整个数组的地址,地址求大小 4/8
	printf("%d\n", sizeof(&arr + 1));//&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8
	printf("%d\n", sizeof(&arr[0] + 1));//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8

3.2 strlen 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };//数组中没有'//从数组首元素地址开始向后,一直到字符'printf'为止,'
	(
	"%d\n",strlen( ))arr;//数组的地址,求长度 随机值printf(
	"%d\n",strlen( +0arr ) );//arr首元素的地址,求长度 随机值//printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误
	printf
	(
	"%d\n",strlen( &))arr;//&arr整个数组的地址, 求长度 随机值printf(
	"%d\n",strlen( &+1arr ) );//&arr + 1移动整个数组的地址,指向数组末尾,还是地址,随机值,和上面差6printf (
	"%d\n",strlen( &[0arr]+1 ) );//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,随机值和上面差1char[

3.3 sizeof 练习 char arr[ ] = “abcdef”
] arr="abcdef" ; //常量字符串,末尾隐藏字符'printf'("%d\n"
	,sizeof() );arr//sizeod(数组名),数组所占内存大小。6个字符 加上末尾隐藏字符'printf',求大小 7("%d\n",
	sizeof(+0 ))arr ; //arr不是2中例外,这里arr+0表示首元素的地址,求大小 4/8printf("%d\n",
	sizeof(*) );//arr表示首元素的地址,*arr取得首元素'a',求大小 1arrprintf("%d\n",
	sizeof([1 ])arr);//arr[1]表示第二个元素'b',求大小 1printf("%d\n",
	sizeof(&) );//&arr整个数组的地址,地址求大小 4/8arrprintf("%d\n",
	sizeof(&+ 1))arr ; //&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8printf("%d\n",
	sizeof(&[ 0]+arr1)) ; //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8char[]=

3.4 strlen 练习 char arr[ ] = “abcdef”
"abcdef" arr;//常量字符串,末尾隐藏字符'printf' ( "%d\n",strlen
	()); //arr数组首元素的地址,求长度 6printfarr("%d\n",strlen
	(+0) );arr //arr首元素的地址,求长度 6 //printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误printf("%d\n"
	,
	strlen
	(&)) ;//&arr整个数组的地址,数值等同首元素的地址 求长度 6printfarr("%d\n",strlen
	(&+1 ));arr //&arr + 1移动跳过整个数组的地址,指向数组末尾,还是地址,随机值 printf("%d\n",strlen
	(&[0 ]+1arr)); //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,5 char*="abcdef";

3.5 sizeof 练习 char *p = “abcdef”
char [p ] ="abcdef"
等效于下面常见的代码,将字符串常量的首地址赋值给指针变量p
	; achar* = &;
	[ 0p ] =a*
	p(+0)=*p(+0)=[a0]char*a="abcdef";

printf (p "%d\n" ,sizeof
	()); //p是指针变量,保存首元素地址,地址求大小 4/8printfp("%d\n",sizeof
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求大小 4/8 printf("%d\n",sizeof
	(*)) ;//*p取出首元素 'a',求大小 1printfp("%d\n",sizeof
	([0] ))p;//p[0]代表首元素 'a',求大小 1printf("%d\n",sizeof
	(&)) ;//&p 是指针变量p在内存中的地址, 地址求大小 4/8printfp("%d\n",sizeof
	(&+1 ));p //4/8 - &p+1是跳过p之后的地址,地址求大小 4/8 printf("%d\n",sizeof
	(&[0 ]+1p)); //4/8 &p[0]是‘a’的地址,&p[0]+1就是b的地址,地址求大小 4/8 char*="abcdef";

3.6 strlen 练习 char *p = “abcdef”
printf (p "%d\n" ,strlen
()); //p是指针变量,保存首元素地址,求长度 6printfp("%d\n",strlen
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求长度 5 //printf("%d\n", strlen(*p));//*p取得首元素 'a' ,97,内存中97这个地址不能访问,类似野指针//printf("%d\n", strlen(p[0]));//p[0]得到首元素 'a',97,内存中97这个地址不能访问,类似野指针printf("%d\n"
	,
	strlen
	(&)) ;//&p 是指针变量p在内存中的地址, 求长度 随机值printfp("%d\n",strlen
	(&+1 ));p // &p+1是跳过p之后的地址, 求长度 随机值  printf("%d\n",strlen
	(&[0 ]+1p)); // &p[0]是首元素‘a’的地址,&p[0]+1就是b的地址,求长度 5 int[3][

4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
4 a]=0};printf ( { "%d\n" ,sizeof
	()); //sizeof(a)求取整个数组的大小,48printfa("%d\n",sizeof
	([0] [0a]));//(a[0][0]是第一行第一个元素,求大小 4printf("%d\n",sizeof
	([0] ))a;//a[0]代表二维数组首元素,即第一行数组的数组名,sizeof(a[0])求第一行数字的大小 16printf("%d\n",sizeof
	([0] +1a)); //a[0]第一行数组的数组名,没有放在sizeof里面,没有单独取地址,因此,a[0]代表第一行数组第1个元素的地址,a[0] +1是第一行数组第二个元素的地址,求大小 4 printf("%d\n",sizeof
	(*([ 0]+1a))) ; //解引用取出第一行第二个元素,求大小 4printf("%d\n",sizeof
	(+1) );a //a不是两个例外,表示二维元素的首元素地址,a+1表示第二个元素的地址,就是第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(+ 1)))a ; //*(a + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(&[0 ]+1a)); //&a[0]第一行数组的地址,&a[0]+1 表示第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(& [0]+1a))) ; //*(&a[0] + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(*)) ;//a为首元素地址,*a取出首元素的内容,即第一行数组, 求大小 16printfa("%d\n",sizeof
	([3] ))a;//地址,a[3]也是int[4] 类型,里面的元素都是随机数值,求大小 16[+++][+++][+++][+++][+++]



总结

本文先复习了一些知识点,尤其是二维数组,要牢记数组名的一般情况和两个例外,通过sizeof 和 strlen 的练习,再次复习了数组和指针的知识点。

这段时间所学知识都是建立在前面的基础之上,知识不牢,地动山摇,要经常对前面所学的知识点进行复习。

若有地方总结错误,也请大家友好指正,谢谢大家! 下一篇继续更新数组和指针的练习。

)
File: /www/wwwroot/outofmemory.cn/tmp/route_read.php, Line: 126, InsideLink()
File: /www/wwwroot/outofmemory.cn/tmp/index.inc.php, Line: 166, include(/www/wwwroot/outofmemory.cn/tmp/route_read.php)
File: /www/wwwroot/outofmemory.cn/index.php, Line: 30, include(/www/wwwroot/outofmemory.cn/tmp/index.inc.php)
Error[8]: Undefined offset: 913, File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 121
File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 473, decode(

指针的进阶(4)- 数组的练习 sizeof 和 strlen


前言

前面已经介绍了数组和指针的知识点,并且用类比方法做了总结。先简要复习与本文练习相关的知识点:

要学以致用,才能更加深入的理解所学的知识点,因此本文主要是数组和指针相关知识点的练习:


1、 相关知识点复习

在前面的学习中,我们经常碰到数组名、sizeof、strlen,本文的练习也会用到它们,先对这些知识点进行复习。

1.1 复习数组名

前面在 【C语言基础5——数组(1)】4.2 和4.3小结 中已经初步学习过了数组名的知识点。

在进阶中更深入的学习了数组和指针后,对数组名理解更加深刻了,温故而知新,首先还是复习下数组名的知识点:

但是有两个例外:

1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
type_t arr_name [const_n];
type_t 是指数组的元素类型
const_n 是一个常量表达式,用来指定数组的大小

学完指针后,对 [ ] 有了更加深刻的理解,将 *** 作符[ ]和取地址 &、定义指针符号 *结合:

1.2.1 一维数组中三者的联系

1.2.2 二维数组中三者的联系


二维数组举例,对照上图和下面的代码分析,可见二维数组的知识点其实是很密集的:

int main()
{
	int a[2][3] = { {1,2,3},{4,5,6 } };
	return 0;
}

注意各个监视对象的类型,类型不一样代表的意义不一样:

1.3 复习sizeof

sizeof 是一个 *** 作符,sizeof 计算的是对象所占内存的大小-单位是字节,不在乎内存中存放的是什么,只在乎内存大小

1.4 复习strlen

strlen 是一个库函数,功能:求字符串长度,从给定的地址向后访问字符,统计\0之前出现的字符个数。

2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
int a[] = { 1,2,3,4 };
	printf("%d\n", sizeof(a));//sizeof(数组名),求取的是整个数组的大小 16
	printf("%d\n", sizeof(a + 0));//数组名不是单独使用,a+0表示首元素的地址,地址的大小就是 4/8
	printf("%d\n", sizeof(*a));//a表示首元素的地址,*a表示数组的首元素,求第一个元素的大小 4
	printf("%d\n", sizeof(a + 1));//a表示首元素的地址,a+1表示第二个元素的地址,求大小 4/8
	printf("%d\n", sizeof(a[1]));//a[1]表示数组第二个元素,求大小 4
	printf("%d\n", sizeof(&a));//&a表示整个数组的地址,求大小 4/8
	printf("%d\n", sizeof(*&a));//*&a 对整个数组的地址解引用,拿到整个数组,求大小 16
	printf("%d\n", sizeof(&a + 1));//&a+1表示跳过一个数组后的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0]));//&a[0]首元素的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0] + 1));//&a[0]+1数组第二个元素的地址,求大小 4/8

3、一维字符数组 3.1 sizeof 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };
	printf("%d\n", sizeof(arr));//sizeod(数组名),所占内存大小。6个字符 ,求大小 6
	printf("%d\n", sizeof(arr + 0));//arr表示首元素的地址,arr+0表示首元素的地址,地址求大小 4/8
	printf("%d\n", sizeof(*arr));//arr表示首元素的地址,*arr取得首元素是一个字符,求大小 1
	printf("%d\n", sizeof(arr[1]));//arr[1]表示第二个元素,是一个字符,求大小 1
	printf("%d\n", sizeof(&arr));//&arr取整个数组的地址,地址求大小 4/8
	printf("%d\n", sizeof(&arr + 1));//&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8
	printf("%d\n", sizeof(&arr[0] + 1));//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8

3.2 strlen 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };//数组中没有'//从数组首元素地址开始向后,一直到字符'printf'为止,'
	(
	"%d\n",strlen( ))arr;//数组的地址,求长度 随机值printf(
	"%d\n",strlen( +0arr ) );//arr首元素的地址,求长度 随机值//printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误
	printf
	(
	"%d\n",strlen( &))arr;//&arr整个数组的地址, 求长度 随机值printf(
	"%d\n",strlen( &+1arr ) );//&arr + 1移动整个数组的地址,指向数组末尾,还是地址,随机值,和上面差6printf (
	"%d\n",strlen( &[0arr]+1 ) );//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,随机值和上面差1char[

3.3 sizeof 练习 char arr[ ] = “abcdef”
] arr="abcdef" ; //常量字符串,末尾隐藏字符'printf'("%d\n"
	,sizeof() );arr//sizeod(数组名),数组所占内存大小。6个字符 加上末尾隐藏字符'printf',求大小 7("%d\n",
	sizeof(+0 ))arr ; //arr不是2中例外,这里arr+0表示首元素的地址,求大小 4/8printf("%d\n",
	sizeof(*) );//arr表示首元素的地址,*arr取得首元素'a',求大小 1arrprintf("%d\n",
	sizeof([1 ])arr);//arr[1]表示第二个元素'b',求大小 1printf("%d\n",
	sizeof(&) );//&arr整个数组的地址,地址求大小 4/8arrprintf("%d\n",
	sizeof(&+ 1))arr ; //&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8printf("%d\n",
	sizeof(&[ 0]+arr1)) ; //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8char[]=

3.4 strlen 练习 char arr[ ] = “abcdef”
"abcdef" arr;//常量字符串,末尾隐藏字符'printf' ( "%d\n",strlen
	()); //arr数组首元素的地址,求长度 6printfarr("%d\n",strlen
	(+0) );arr //arr首元素的地址,求长度 6 //printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误printf("%d\n"
	,
	strlen
	(&)) ;//&arr整个数组的地址,数值等同首元素的地址 求长度 6printfarr("%d\n",strlen
	(&+1 ));arr //&arr + 1移动跳过整个数组的地址,指向数组末尾,还是地址,随机值 printf("%d\n",strlen
	(&[0 ]+1arr)); //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,5 char*="abcdef";

3.5 sizeof 练习 char *p = “abcdef”
char [p ] ="abcdef"
等效于下面常见的代码,将字符串常量的首地址赋值给指针变量p
	; achar* = &;
	[ 0p ] =a*
	p(+0)=*p(+0)=[a0]char*a="abcdef";

printf (p "%d\n" ,sizeof
	()); //p是指针变量,保存首元素地址,地址求大小 4/8printfp("%d\n",sizeof
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求大小 4/8 printf("%d\n",sizeof
	(*)) ;//*p取出首元素 'a',求大小 1printfp("%d\n",sizeof
	([0] ))p;//p[0]代表首元素 'a',求大小 1printf("%d\n",sizeof
	(&)) ;//&p 是指针变量p在内存中的地址, 地址求大小 4/8printfp("%d\n",sizeof
	(&+1 ));p //4/8 - &p+1是跳过p之后的地址,地址求大小 4/8 printf("%d\n",sizeof
	(&[0 ]+1p)); //4/8 &p[0]是‘a’的地址,&p[0]+1就是b的地址,地址求大小 4/8 char*="abcdef";

3.6 strlen 练习 char *p = “abcdef”
printf (p "%d\n" ,strlen
()); //p是指针变量,保存首元素地址,求长度 6printfp("%d\n",strlen
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求长度 5 //printf("%d\n", strlen(*p));//*p取得首元素 'a' ,97,内存中97这个地址不能访问,类似野指针//printf("%d\n", strlen(p[0]));//p[0]得到首元素 'a',97,内存中97这个地址不能访问,类似野指针printf("%d\n"
	,
	strlen
	(&)) ;//&p 是指针变量p在内存中的地址, 求长度 随机值printfp("%d\n",strlen
	(&+1 ));p // &p+1是跳过p之后的地址, 求长度 随机值  printf("%d\n",strlen
	(&[0 ]+1p)); // &p[0]是首元素‘a’的地址,&p[0]+1就是b的地址,求长度 5 int[3][

4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
4 a]=0};printf ( { "%d\n" ,sizeof
	()); //sizeof(a)求取整个数组的大小,48printfa("%d\n",sizeof
	([0] [0a]));//(a[0][0]是第一行第一个元素,求大小 4printf("%d\n",sizeof
	([0] ))a;//a[0]代表二维数组首元素,即第一行数组的数组名,sizeof(a[0])求第一行数字的大小 16printf("%d\n",sizeof
	([0] +1a)); //a[0]第一行数组的数组名,没有放在sizeof里面,没有单独取地址,因此,a[0]代表第一行数组第1个元素的地址,a[0] +1是第一行数组第二个元素的地址,求大小 4 printf("%d\n",sizeof
	(*([ 0]+1a))) ; //解引用取出第一行第二个元素,求大小 4printf("%d\n",sizeof
	(+1) );a //a不是两个例外,表示二维元素的首元素地址,a+1表示第二个元素的地址,就是第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(+ 1)))a ; //*(a + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(&[0 ]+1a)); //&a[0]第一行数组的地址,&a[0]+1 表示第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(& [0]+1a))) ; //*(&a[0] + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(*)) ;//a为首元素地址,*a取出首元素的内容,即第一行数组, 求大小 16printfa("%d\n",sizeof
	([3] ))a;//地址,a[3]也是int[4] 类型,里面的元素都是随机数值,求大小 16[+++][+++][+++][+++]



总结

本文先复习了一些知识点,尤其是二维数组,要牢记数组名的一般情况和两个例外,通过sizeof 和 strlen 的练习,再次复习了数组和指针的知识点。

这段时间所学知识都是建立在前面的基础之上,知识不牢,地动山摇,要经常对前面所学的知识点进行复习。

若有地方总结错误,也请大家友好指正,谢谢大家! 下一篇继续更新数组和指针的练习。

)
File: /www/wwwroot/outofmemory.cn/tmp/route_read.php, Line: 126, InsideLink()
File: /www/wwwroot/outofmemory.cn/tmp/index.inc.php, Line: 166, include(/www/wwwroot/outofmemory.cn/tmp/route_read.php)
File: /www/wwwroot/outofmemory.cn/index.php, Line: 30, include(/www/wwwroot/outofmemory.cn/tmp/index.inc.php)
Error[8]: Undefined offset: 914, File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 121
File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 473, decode(

指针的进阶(4)- 数组的练习 sizeof 和 strlen


前言

前面已经介绍了数组和指针的知识点,并且用类比方法做了总结。先简要复习与本文练习相关的知识点:

要学以致用,才能更加深入的理解所学的知识点,因此本文主要是数组和指针相关知识点的练习:


1、 相关知识点复习

在前面的学习中,我们经常碰到数组名、sizeof、strlen,本文的练习也会用到它们,先对这些知识点进行复习。

1.1 复习数组名

前面在 【C语言基础5——数组(1)】4.2 和4.3小结 中已经初步学习过了数组名的知识点。

在进阶中更深入的学习了数组和指针后,对数组名理解更加深刻了,温故而知新,首先还是复习下数组名的知识点:

但是有两个例外:

1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
type_t arr_name [const_n];
type_t 是指数组的元素类型
const_n 是一个常量表达式,用来指定数组的大小

学完指针后,对 [ ] 有了更加深刻的理解,将 *** 作符[ ]和取地址 &、定义指针符号 *结合:

1.2.1 一维数组中三者的联系

1.2.2 二维数组中三者的联系


二维数组举例,对照上图和下面的代码分析,可见二维数组的知识点其实是很密集的:

int main()
{
	int a[2][3] = { {1,2,3},{4,5,6 } };
	return 0;
}

注意各个监视对象的类型,类型不一样代表的意义不一样:

1.3 复习sizeof

sizeof 是一个 *** 作符,sizeof 计算的是对象所占内存的大小-单位是字节,不在乎内存中存放的是什么,只在乎内存大小

1.4 复习strlen

strlen 是一个库函数,功能:求字符串长度,从给定的地址向后访问字符,统计\0之前出现的字符个数。

2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
int a[] = { 1,2,3,4 };
	printf("%d\n", sizeof(a));//sizeof(数组名),求取的是整个数组的大小 16
	printf("%d\n", sizeof(a + 0));//数组名不是单独使用,a+0表示首元素的地址,地址的大小就是 4/8
	printf("%d\n", sizeof(*a));//a表示首元素的地址,*a表示数组的首元素,求第一个元素的大小 4
	printf("%d\n", sizeof(a + 1));//a表示首元素的地址,a+1表示第二个元素的地址,求大小 4/8
	printf("%d\n", sizeof(a[1]));//a[1]表示数组第二个元素,求大小 4
	printf("%d\n", sizeof(&a));//&a表示整个数组的地址,求大小 4/8
	printf("%d\n", sizeof(*&a));//*&a 对整个数组的地址解引用,拿到整个数组,求大小 16
	printf("%d\n", sizeof(&a + 1));//&a+1表示跳过一个数组后的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0]));//&a[0]首元素的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0] + 1));//&a[0]+1数组第二个元素的地址,求大小 4/8

3、一维字符数组 3.1 sizeof 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };
	printf("%d\n", sizeof(arr));//sizeod(数组名),所占内存大小。6个字符 ,求大小 6
	printf("%d\n", sizeof(arr + 0));//arr表示首元素的地址,arr+0表示首元素的地址,地址求大小 4/8
	printf("%d\n", sizeof(*arr));//arr表示首元素的地址,*arr取得首元素是一个字符,求大小 1
	printf("%d\n", sizeof(arr[1]));//arr[1]表示第二个元素,是一个字符,求大小 1
	printf("%d\n", sizeof(&arr));//&arr取整个数组的地址,地址求大小 4/8
	printf("%d\n", sizeof(&arr + 1));//&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8
	printf("%d\n", sizeof(&arr[0] + 1));//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8

3.2 strlen 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };//数组中没有'//从数组首元素地址开始向后,一直到字符'printf'为止,'
	(
	"%d\n",strlen( ))arr;//数组的地址,求长度 随机值printf(
	"%d\n",strlen( +0arr ) );//arr首元素的地址,求长度 随机值//printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误
	printf
	(
	"%d\n",strlen( &))arr;//&arr整个数组的地址, 求长度 随机值printf(
	"%d\n",strlen( &+1arr ) );//&arr + 1移动整个数组的地址,指向数组末尾,还是地址,随机值,和上面差6printf (
	"%d\n",strlen( &[0arr]+1 ) );//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,随机值和上面差1char[

3.3 sizeof 练习 char arr[ ] = “abcdef”
] arr="abcdef" ; //常量字符串,末尾隐藏字符'printf'("%d\n"
	,sizeof() );arr//sizeod(数组名),数组所占内存大小。6个字符 加上末尾隐藏字符'printf',求大小 7("%d\n",
	sizeof(+0 ))arr ; //arr不是2中例外,这里arr+0表示首元素的地址,求大小 4/8printf("%d\n",
	sizeof(*) );//arr表示首元素的地址,*arr取得首元素'a',求大小 1arrprintf("%d\n",
	sizeof([1 ])arr);//arr[1]表示第二个元素'b',求大小 1printf("%d\n",
	sizeof(&) );//&arr整个数组的地址,地址求大小 4/8arrprintf("%d\n",
	sizeof(&+ 1))arr ; //&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8printf("%d\n",
	sizeof(&[ 0]+arr1)) ; //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8char[]=

3.4 strlen 练习 char arr[ ] = “abcdef”
"abcdef" arr;//常量字符串,末尾隐藏字符'printf' ( "%d\n",strlen
	()); //arr数组首元素的地址,求长度 6printfarr("%d\n",strlen
	(+0) );arr //arr首元素的地址,求长度 6 //printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误printf("%d\n"
	,
	strlen
	(&)) ;//&arr整个数组的地址,数值等同首元素的地址 求长度 6printfarr("%d\n",strlen
	(&+1 ));arr //&arr + 1移动跳过整个数组的地址,指向数组末尾,还是地址,随机值 printf("%d\n",strlen
	(&[0 ]+1arr)); //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,5 char*="abcdef";

3.5 sizeof 练习 char *p = “abcdef”
char [p ] ="abcdef"
等效于下面常见的代码,将字符串常量的首地址赋值给指针变量p
	; achar* = &;
	[ 0p ] =a*
	p(+0)=*p(+0)=[a0]char*a="abcdef";

printf (p "%d\n" ,sizeof
	()); //p是指针变量,保存首元素地址,地址求大小 4/8printfp("%d\n",sizeof
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求大小 4/8 printf("%d\n",sizeof
	(*)) ;//*p取出首元素 'a',求大小 1printfp("%d\n",sizeof
	([0] ))p;//p[0]代表首元素 'a',求大小 1printf("%d\n",sizeof
	(&)) ;//&p 是指针变量p在内存中的地址, 地址求大小 4/8printfp("%d\n",sizeof
	(&+1 ));p //4/8 - &p+1是跳过p之后的地址,地址求大小 4/8 printf("%d\n",sizeof
	(&[0 ]+1p)); //4/8 &p[0]是‘a’的地址,&p[0]+1就是b的地址,地址求大小 4/8 char*="abcdef";

3.6 strlen 练习 char *p = “abcdef”
printf (p "%d\n" ,strlen
()); //p是指针变量,保存首元素地址,求长度 6printfp("%d\n",strlen
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求长度 5 //printf("%d\n", strlen(*p));//*p取得首元素 'a' ,97,内存中97这个地址不能访问,类似野指针//printf("%d\n", strlen(p[0]));//p[0]得到首元素 'a',97,内存中97这个地址不能访问,类似野指针printf("%d\n"
	,
	strlen
	(&)) ;//&p 是指针变量p在内存中的地址, 求长度 随机值printfp("%d\n",strlen
	(&+1 ));p // &p+1是跳过p之后的地址, 求长度 随机值  printf("%d\n",strlen
	(&[0 ]+1p)); // &p[0]是首元素‘a’的地址,&p[0]+1就是b的地址,求长度 5 int[3][

4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
4 a]=0};printf ( { "%d\n" ,sizeof
	()); //sizeof(a)求取整个数组的大小,48printfa("%d\n",sizeof
	([0] [0a]));//(a[0][0]是第一行第一个元素,求大小 4printf("%d\n",sizeof
	([0] ))a;//a[0]代表二维数组首元素,即第一行数组的数组名,sizeof(a[0])求第一行数字的大小 16printf("%d\n",sizeof
	([0] +1a)); //a[0]第一行数组的数组名,没有放在sizeof里面,没有单独取地址,因此,a[0]代表第一行数组第1个元素的地址,a[0] +1是第一行数组第二个元素的地址,求大小 4 printf("%d\n",sizeof
	(*([ 0]+1a))) ; //解引用取出第一行第二个元素,求大小 4printf("%d\n",sizeof
	(+1) );a //a不是两个例外,表示二维元素的首元素地址,a+1表示第二个元素的地址,就是第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(+ 1)))a ; //*(a + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(&[0 ]+1a)); //&a[0]第一行数组的地址,&a[0]+1 表示第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(& [0]+1a))) ; //*(&a[0] + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(*)) ;//a为首元素地址,*a取出首元素的内容,即第一行数组, 求大小 16printfa("%d\n",sizeof
	([3] ))a;//地址,a[3]也是int[4] 类型,里面的元素都是随机数值,求大小 16[+++][+++][+++]



总结

本文先复习了一些知识点,尤其是二维数组,要牢记数组名的一般情况和两个例外,通过sizeof 和 strlen 的练习,再次复习了数组和指针的知识点。

这段时间所学知识都是建立在前面的基础之上,知识不牢,地动山摇,要经常对前面所学的知识点进行复习。

若有地方总结错误,也请大家友好指正,谢谢大家! 下一篇继续更新数组和指针的练习。

)
File: /www/wwwroot/outofmemory.cn/tmp/route_read.php, Line: 126, InsideLink()
File: /www/wwwroot/outofmemory.cn/tmp/index.inc.php, Line: 166, include(/www/wwwroot/outofmemory.cn/tmp/route_read.php)
File: /www/wwwroot/outofmemory.cn/index.php, Line: 30, include(/www/wwwroot/outofmemory.cn/tmp/index.inc.php)
Error[8]: Undefined offset: 915, File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 121
File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 473, decode(

指针的进阶(4)- 数组的练习 sizeof 和 strlen


前言

前面已经介绍了数组和指针的知识点,并且用类比方法做了总结。先简要复习与本文练习相关的知识点:

要学以致用,才能更加深入的理解所学的知识点,因此本文主要是数组和指针相关知识点的练习:


1、 相关知识点复习

在前面的学习中,我们经常碰到数组名、sizeof、strlen,本文的练习也会用到它们,先对这些知识点进行复习。

1.1 复习数组名

前面在 【C语言基础5——数组(1)】4.2 和4.3小结 中已经初步学习过了数组名的知识点。

在进阶中更深入的学习了数组和指针后,对数组名理解更加深刻了,温故而知新,首先还是复习下数组名的知识点:

但是有两个例外:

1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
type_t arr_name [const_n];
type_t 是指数组的元素类型
const_n 是一个常量表达式,用来指定数组的大小

学完指针后,对 [ ] 有了更加深刻的理解,将 *** 作符[ ]和取地址 &、定义指针符号 *结合:

1.2.1 一维数组中三者的联系

1.2.2 二维数组中三者的联系


二维数组举例,对照上图和下面的代码分析,可见二维数组的知识点其实是很密集的:

int main()
{
	int a[2][3] = { {1,2,3},{4,5,6 } };
	return 0;
}

注意各个监视对象的类型,类型不一样代表的意义不一样:

1.3 复习sizeof

sizeof 是一个 *** 作符,sizeof 计算的是对象所占内存的大小-单位是字节,不在乎内存中存放的是什么,只在乎内存大小

1.4 复习strlen

strlen 是一个库函数,功能:求字符串长度,从给定的地址向后访问字符,统计\0之前出现的字符个数。

2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
int a[] = { 1,2,3,4 };
	printf("%d\n", sizeof(a));//sizeof(数组名),求取的是整个数组的大小 16
	printf("%d\n", sizeof(a + 0));//数组名不是单独使用,a+0表示首元素的地址,地址的大小就是 4/8
	printf("%d\n", sizeof(*a));//a表示首元素的地址,*a表示数组的首元素,求第一个元素的大小 4
	printf("%d\n", sizeof(a + 1));//a表示首元素的地址,a+1表示第二个元素的地址,求大小 4/8
	printf("%d\n", sizeof(a[1]));//a[1]表示数组第二个元素,求大小 4
	printf("%d\n", sizeof(&a));//&a表示整个数组的地址,求大小 4/8
	printf("%d\n", sizeof(*&a));//*&a 对整个数组的地址解引用,拿到整个数组,求大小 16
	printf("%d\n", sizeof(&a + 1));//&a+1表示跳过一个数组后的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0]));//&a[0]首元素的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0] + 1));//&a[0]+1数组第二个元素的地址,求大小 4/8

3、一维字符数组 3.1 sizeof 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };
	printf("%d\n", sizeof(arr));//sizeod(数组名),所占内存大小。6个字符 ,求大小 6
	printf("%d\n", sizeof(arr + 0));//arr表示首元素的地址,arr+0表示首元素的地址,地址求大小 4/8
	printf("%d\n", sizeof(*arr));//arr表示首元素的地址,*arr取得首元素是一个字符,求大小 1
	printf("%d\n", sizeof(arr[1]));//arr[1]表示第二个元素,是一个字符,求大小 1
	printf("%d\n", sizeof(&arr));//&arr取整个数组的地址,地址求大小 4/8
	printf("%d\n", sizeof(&arr + 1));//&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8
	printf("%d\n", sizeof(&arr[0] + 1));//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8

3.2 strlen 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };//数组中没有'//从数组首元素地址开始向后,一直到字符'printf'为止,'
	(
	"%d\n",strlen( ))arr;//数组的地址,求长度 随机值printf(
	"%d\n",strlen( +0arr ) );//arr首元素的地址,求长度 随机值//printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误
	printf
	(
	"%d\n",strlen( &))arr;//&arr整个数组的地址, 求长度 随机值printf(
	"%d\n",strlen( &+1arr ) );//&arr + 1移动整个数组的地址,指向数组末尾,还是地址,随机值,和上面差6printf (
	"%d\n",strlen( &[0arr]+1 ) );//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,随机值和上面差1char[

3.3 sizeof 练习 char arr[ ] = “abcdef”
] arr="abcdef" ; //常量字符串,末尾隐藏字符'printf'("%d\n"
	,sizeof() );arr//sizeod(数组名),数组所占内存大小。6个字符 加上末尾隐藏字符'printf',求大小 7("%d\n",
	sizeof(+0 ))arr ; //arr不是2中例外,这里arr+0表示首元素的地址,求大小 4/8printf("%d\n",
	sizeof(*) );//arr表示首元素的地址,*arr取得首元素'a',求大小 1arrprintf("%d\n",
	sizeof([1 ])arr);//arr[1]表示第二个元素'b',求大小 1printf("%d\n",
	sizeof(&) );//&arr整个数组的地址,地址求大小 4/8arrprintf("%d\n",
	sizeof(&+ 1))arr ; //&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8printf("%d\n",
	sizeof(&[ 0]+arr1)) ; //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8char[]=

3.4 strlen 练习 char arr[ ] = “abcdef”
"abcdef" arr;//常量字符串,末尾隐藏字符'printf' ( "%d\n",strlen
	()); //arr数组首元素的地址,求长度 6printfarr("%d\n",strlen
	(+0) );arr //arr首元素的地址,求长度 6 //printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误printf("%d\n"
	,
	strlen
	(&)) ;//&arr整个数组的地址,数值等同首元素的地址 求长度 6printfarr("%d\n",strlen
	(&+1 ));arr //&arr + 1移动跳过整个数组的地址,指向数组末尾,还是地址,随机值 printf("%d\n",strlen
	(&[0 ]+1arr)); //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,5 char*="abcdef";

3.5 sizeof 练习 char *p = “abcdef”
char [p ] ="abcdef"
等效于下面常见的代码,将字符串常量的首地址赋值给指针变量p
	; achar* = &;
	[ 0p ] =a*
	p(+0)=*p(+0)=[a0]char*a="abcdef";

printf (p "%d\n" ,sizeof
	()); //p是指针变量,保存首元素地址,地址求大小 4/8printfp("%d\n",sizeof
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求大小 4/8 printf("%d\n",sizeof
	(*)) ;//*p取出首元素 'a',求大小 1printfp("%d\n",sizeof
	([0] ))p;//p[0]代表首元素 'a',求大小 1printf("%d\n",sizeof
	(&)) ;//&p 是指针变量p在内存中的地址, 地址求大小 4/8printfp("%d\n",sizeof
	(&+1 ));p //4/8 - &p+1是跳过p之后的地址,地址求大小 4/8 printf("%d\n",sizeof
	(&[0 ]+1p)); //4/8 &p[0]是‘a’的地址,&p[0]+1就是b的地址,地址求大小 4/8 char*="abcdef";

3.6 strlen 练习 char *p = “abcdef”
printf (p "%d\n" ,strlen
()); //p是指针变量,保存首元素地址,求长度 6printfp("%d\n",strlen
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求长度 5 //printf("%d\n", strlen(*p));//*p取得首元素 'a' ,97,内存中97这个地址不能访问,类似野指针//printf("%d\n", strlen(p[0]));//p[0]得到首元素 'a',97,内存中97这个地址不能访问,类似野指针printf("%d\n"
	,
	strlen
	(&)) ;//&p 是指针变量p在内存中的地址, 求长度 随机值printfp("%d\n",strlen
	(&+1 ));p // &p+1是跳过p之后的地址, 求长度 随机值  printf("%d\n",strlen
	(&[0 ]+1p)); // &p[0]是首元素‘a’的地址,&p[0]+1就是b的地址,求长度 5 int[3][

4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
4 a]=0};printf ( { "%d\n" ,sizeof
	()); //sizeof(a)求取整个数组的大小,48printfa("%d\n",sizeof
	([0] [0a]));//(a[0][0]是第一行第一个元素,求大小 4printf("%d\n",sizeof
	([0] ))a;//a[0]代表二维数组首元素,即第一行数组的数组名,sizeof(a[0])求第一行数字的大小 16printf("%d\n",sizeof
	([0] +1a)); //a[0]第一行数组的数组名,没有放在sizeof里面,没有单独取地址,因此,a[0]代表第一行数组第1个元素的地址,a[0] +1是第一行数组第二个元素的地址,求大小 4 printf("%d\n",sizeof
	(*([ 0]+1a))) ; //解引用取出第一行第二个元素,求大小 4printf("%d\n",sizeof
	(+1) );a //a不是两个例外,表示二维元素的首元素地址,a+1表示第二个元素的地址,就是第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(+ 1)))a ; //*(a + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(&[0 ]+1a)); //&a[0]第一行数组的地址,&a[0]+1 表示第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(& [0]+1a))) ; //*(&a[0] + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(*)) ;//a为首元素地址,*a取出首元素的内容,即第一行数组, 求大小 16printfa("%d\n",sizeof
	([3] ))a;//地址,a[3]也是int[4] 类型,里面的元素都是随机数值,求大小 16[+++][+++]



总结

本文先复习了一些知识点,尤其是二维数组,要牢记数组名的一般情况和两个例外,通过sizeof 和 strlen 的练习,再次复习了数组和指针的知识点。

这段时间所学知识都是建立在前面的基础之上,知识不牢,地动山摇,要经常对前面所学的知识点进行复习。

若有地方总结错误,也请大家友好指正,谢谢大家! 下一篇继续更新数组和指针的练习。

)
File: /www/wwwroot/outofmemory.cn/tmp/route_read.php, Line: 126, InsideLink()
File: /www/wwwroot/outofmemory.cn/tmp/index.inc.php, Line: 166, include(/www/wwwroot/outofmemory.cn/tmp/route_read.php)
File: /www/wwwroot/outofmemory.cn/index.php, Line: 30, include(/www/wwwroot/outofmemory.cn/tmp/index.inc.php)
Error[8]: Undefined offset: 916, File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 121
File: /www/wwwroot/outofmemory.cn/tmp/plugin_ss_superseo_model_superseo.php, Line: 473, decode(

指针的进阶(4)- 数组的练习 sizeof 和 strlen


前言

前面已经介绍了数组和指针的知识点,并且用类比方法做了总结。先简要复习与本文练习相关的知识点:

要学以致用,才能更加深入的理解所学的知识点,因此本文主要是数组和指针相关知识点的练习:


1、 相关知识点复习

在前面的学习中,我们经常碰到数组名、sizeof、strlen,本文的练习也会用到它们,先对这些知识点进行复习。

1.1 复习数组名

前面在 【C语言基础5——数组(1)】4.2 和4.3小结 中已经初步学习过了数组名的知识点。

在进阶中更深入的学习了数组和指针后,对数组名理解更加深刻了,温故而知新,首先还是复习下数组名的知识点:

但是有两个例外:

1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
type_t arr_name [const_n];
type_t 是指数组的元素类型
const_n 是一个常量表达式,用来指定数组的大小

学完指针后,对 [ ] 有了更加深刻的理解,将 *** 作符[ ]和取地址 &、定义指针符号 *结合:

1.2.1 一维数组中三者的联系

1.2.2 二维数组中三者的联系


二维数组举例,对照上图和下面的代码分析,可见二维数组的知识点其实是很密集的:

int main()
{
	int a[2][3] = { {1,2,3},{4,5,6 } };
	return 0;
}

注意各个监视对象的类型,类型不一样代表的意义不一样:

1.3 复习sizeof

sizeof 是一个 *** 作符,sizeof 计算的是对象所占内存的大小-单位是字节,不在乎内存中存放的是什么,只在乎内存大小

1.4 复习strlen

strlen 是一个库函数,功能:求字符串长度,从给定的地址向后访问字符,统计\0之前出现的字符个数。

2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
int a[] = { 1,2,3,4 };
	printf("%d\n", sizeof(a));//sizeof(数组名),求取的是整个数组的大小 16
	printf("%d\n", sizeof(a + 0));//数组名不是单独使用,a+0表示首元素的地址,地址的大小就是 4/8
	printf("%d\n", sizeof(*a));//a表示首元素的地址,*a表示数组的首元素,求第一个元素的大小 4
	printf("%d\n", sizeof(a + 1));//a表示首元素的地址,a+1表示第二个元素的地址,求大小 4/8
	printf("%d\n", sizeof(a[1]));//a[1]表示数组第二个元素,求大小 4
	printf("%d\n", sizeof(&a));//&a表示整个数组的地址,求大小 4/8
	printf("%d\n", sizeof(*&a));//*&a 对整个数组的地址解引用,拿到整个数组,求大小 16
	printf("%d\n", sizeof(&a + 1));//&a+1表示跳过一个数组后的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0]));//&a[0]首元素的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0] + 1));//&a[0]+1数组第二个元素的地址,求大小 4/8

3、一维字符数组 3.1 sizeof 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };
	printf("%d\n", sizeof(arr));//sizeod(数组名),所占内存大小。6个字符 ,求大小 6
	printf("%d\n", sizeof(arr + 0));//arr表示首元素的地址,arr+0表示首元素的地址,地址求大小 4/8
	printf("%d\n", sizeof(*arr));//arr表示首元素的地址,*arr取得首元素是一个字符,求大小 1
	printf("%d\n", sizeof(arr[1]));//arr[1]表示第二个元素,是一个字符,求大小 1
	printf("%d\n", sizeof(&arr));//&arr取整个数组的地址,地址求大小 4/8
	printf("%d\n", sizeof(&arr + 1));//&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8
	printf("%d\n", sizeof(&arr[0] + 1));//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8

3.2 strlen 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };//数组中没有'//从数组首元素地址开始向后,一直到字符'printf'为止,'
	(
	"%d\n",strlen( ))arr;//数组的地址,求长度 随机值printf(
	"%d\n",strlen( +0arr ) );//arr首元素的地址,求长度 随机值//printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误
	printf
	(
	"%d\n",strlen( &))arr;//&arr整个数组的地址, 求长度 随机值printf(
	"%d\n",strlen( &+1arr ) );//&arr + 1移动整个数组的地址,指向数组末尾,还是地址,随机值,和上面差6printf (
	"%d\n",strlen( &[0arr]+1 ) );//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,随机值和上面差1char[

3.3 sizeof 练习 char arr[ ] = “abcdef”
] arr="abcdef" ; //常量字符串,末尾隐藏字符'printf'("%d\n"
	,sizeof() );arr//sizeod(数组名),数组所占内存大小。6个字符 加上末尾隐藏字符'printf',求大小 7("%d\n",
	sizeof(+0 ))arr ; //arr不是2中例外,这里arr+0表示首元素的地址,求大小 4/8printf("%d\n",
	sizeof(*) );//arr表示首元素的地址,*arr取得首元素'a',求大小 1arrprintf("%d\n",
	sizeof([1 ])arr);//arr[1]表示第二个元素'b',求大小 1printf("%d\n",
	sizeof(&) );//&arr整个数组的地址,地址求大小 4/8arrprintf("%d\n",
	sizeof(&+ 1))arr ; //&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8printf("%d\n",
	sizeof(&[ 0]+arr1)) ; //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8char[]=

3.4 strlen 练习 char arr[ ] = “abcdef”
"abcdef" arr;//常量字符串,末尾隐藏字符'printf' ( "%d\n",strlen
	()); //arr数组首元素的地址,求长度 6printfarr("%d\n",strlen
	(+0) );arr //arr首元素的地址,求长度 6 //printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误printf("%d\n"
	,
	strlen
	(&)) ;//&arr整个数组的地址,数值等同首元素的地址 求长度 6printfarr("%d\n",strlen
	(&+1 ));arr //&arr + 1移动跳过整个数组的地址,指向数组末尾,还是地址,随机值 printf("%d\n",strlen
	(&[0 ]+1arr)); //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,5 char*="abcdef";

3.5 sizeof 练习 char *p = “abcdef”
char [p ] ="abcdef"
等效于下面常见的代码,将字符串常量的首地址赋值给指针变量p
	; achar* = &;
	[ 0p ] =a*
	p(+0)=*p(+0)=[a0]char*a="abcdef";

printf (p "%d\n" ,sizeof
	()); //p是指针变量,保存首元素地址,地址求大小 4/8printfp("%d\n",sizeof
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求大小 4/8 printf("%d\n",sizeof
	(*)) ;//*p取出首元素 'a',求大小 1printfp("%d\n",sizeof
	([0] ))p;//p[0]代表首元素 'a',求大小 1printf("%d\n",sizeof
	(&)) ;//&p 是指针变量p在内存中的地址, 地址求大小 4/8printfp("%d\n",sizeof
	(&+1 ));p //4/8 - &p+1是跳过p之后的地址,地址求大小 4/8 printf("%d\n",sizeof
	(&[0 ]+1p)); //4/8 &p[0]是‘a’的地址,&p[0]+1就是b的地址,地址求大小 4/8 char*="abcdef";

3.6 strlen 练习 char *p = “abcdef”
printf (p "%d\n" ,strlen
()); //p是指针变量,保存首元素地址,求长度 6printfp("%d\n",strlen
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求长度 5 //printf("%d\n", strlen(*p));//*p取得首元素 'a' ,97,内存中97这个地址不能访问,类似野指针//printf("%d\n", strlen(p[0]));//p[0]得到首元素 'a',97,内存中97这个地址不能访问,类似野指针printf("%d\n"
	,
	strlen
	(&)) ;//&p 是指针变量p在内存中的地址, 求长度 随机值printfp("%d\n",strlen
	(&+1 ));p // &p+1是跳过p之后的地址, 求长度 随机值  printf("%d\n",strlen
	(&[0 ]+1p)); // &p[0]是首元素‘a’的地址,&p[0]+1就是b的地址,求长度 5 int[3][

4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
4 a]=0};printf ( { "%d\n" ,sizeof
	()); //sizeof(a)求取整个数组的大小,48printfa("%d\n",sizeof
	([0] [0a]));//(a[0][0]是第一行第一个元素,求大小 4printf("%d\n",sizeof
	([0] ))a;//a[0]代表二维数组首元素,即第一行数组的数组名,sizeof(a[0])求第一行数字的大小 16printf("%d\n",sizeof
	([0] +1a)); //a[0]第一行数组的数组名,没有放在sizeof里面,没有单独取地址,因此,a[0]代表第一行数组第1个元素的地址,a[0] +1是第一行数组第二个元素的地址,求大小 4 printf("%d\n",sizeof
	(*([ 0]+1a))) ; //解引用取出第一行第二个元素,求大小 4printf("%d\n",sizeof
	(+1) );a //a不是两个例外,表示二维元素的首元素地址,a+1表示第二个元素的地址,就是第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(+ 1)))a ; //*(a + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(&[0 ]+1a)); //&a[0]第一行数组的地址,&a[0]+1 表示第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(& [0]+1a))) ; //*(&a[0] + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(*)) ;//a为首元素地址,*a取出首元素的内容,即第一行数组, 求大小 16printfa("%d\n",sizeof
	([3] ))a;//地址,a[3]也是int[4] 类型,里面的元素都是随机数值,求大小 16[+++]



总结

本文先复习了一些知识点,尤其是二维数组,要牢记数组名的一般情况和两个例外,通过sizeof 和 strlen 的练习,再次复习了数组和指针的知识点。

这段时间所学知识都是建立在前面的基础之上,知识不牢,地动山摇,要经常对前面所学的知识点进行复习。

若有地方总结错误,也请大家友好指正,谢谢大家! 下一篇继续更新数组和指针的练习。

)
File: /www/wwwroot/outofmemory.cn/tmp/route_read.php, Line: 126, InsideLink()
File: /www/wwwroot/outofmemory.cn/tmp/index.inc.php, Line: 166, include(/www/wwwroot/outofmemory.cn/tmp/route_read.php)
File: /www/wwwroot/outofmemory.cn/index.php, Line: 30, include(/www/wwwroot/outofmemory.cn/tmp/index.inc.php)
【C语言进阶7——指针的进阶(4)- 数组的练习 sizeof 和 strlen】_C_内存溢出

【C语言进阶7——指针的进阶(4)- 数组的练习 sizeof 和 strlen】

【C语言进阶7——指针的进阶(4)- 数组的练习 sizeof 和 strlen】,第1张

指针的进阶(4)- 数组的练习 sizeof 和 strlen
  • 前言
  • 1、 相关知识点复习
    • 1.1 复习数组名
    • 1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
      • 1.2.1 一维数组中三者的联系
      • 1.2.2 二维数组中三者的联系
    • 1.3 复习sizeof
    • 1.4 复习strlen
  • 2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
  • 3、一维字符数组
    • 3.1 sizeof 练习 char arr[ ] = { 'a','b','c','d','e','f' }
    • 3.2 strlen 练习 char arr[ ] = { 'a','b','c','d','e','f' }
    • 3.3 sizeof 练习 char arr[ ] = "abcdef"
    • 3.4 strlen 练习 char arr[ ] = "abcdef"
    • 3.5 sizeof 练习 char *p = "abcdef"
    • 3.6 strlen 练习 char *p = "abcdef"
  • 4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
  • 总结


前言

前面已经介绍了数组和指针的知识点,并且用类比方法做了总结。先简要复习与本文练习相关的知识点:

  • 复习数组名
  • *** 作符[ ] 和取地址 & 和 指针符号* 三者分别在一维和二维数组中,相互之间的联系
  • 复习sizeof
  • 复习strlen

要学以致用,才能更加深入的理解所学的知识点,因此本文主要是数组和指针相关知识点的练习:


1、 相关知识点复习

在前面的学习中,我们经常碰到数组名、sizeof、strlen,本文的练习也会用到它们,先对这些知识点进行复习。

1.1 复习数组名

前面在 【C语言基础5——数组(1)】4.2 和4.3小结 中已经初步学习过了数组名的知识点。

在进阶中更深入的学习了数组和指针后,对数组名理解更加深刻了,温故而知新,首先还是复习下数组名的知识点:

  • 数组名一般情况都是表示数组首元素的地址

但是有两个例外:

  • sizeof(数组名),这里数组名表示的是整个数组,求取的整个数组的大小
  • &数组名,表示对整个数组取地址
1.2 *** 作符 [ ] 和取地址 & 和 指针符号* 三者之间的联系
type_t arr_name [const_n];
type_t 是指数组的元素类型
const_n 是一个常量表达式,用来指定数组的大小

学完指针后,对 [ ] 有了更加深刻的理解,将 *** 作符[ ]和取地址 &、定义指针符号 *结合:

1.2.1 一维数组中三者的联系

1.2.2 二维数组中三者的联系


二维数组举例,对照上图和下面的代码分析,可见二维数组的知识点其实是很密集的:

int main()
{
	int a[2][3] = { {1,2,3},{4,5,6 } };
	return 0;
}

注意各个监视对象的类型,类型不一样代表的意义不一样:

1.3 复习sizeof

sizeof 是一个 *** 作符,sizeof 计算的是对象所占内存的大小-单位是字节,不在乎内存中存放的是什么,只在乎内存大小

1.4 复习strlen

strlen 是一个库函数,功能:求字符串长度,从给定的地址向后访问字符,统计\0之前出现的字符个数。

2、 sizeof 一维整形数组 int a[] = { 1,2,3,4 }
int a[] = { 1,2,3,4 };
	printf("%d\n", sizeof(a));//sizeof(数组名),求取的是整个数组的大小 16
	printf("%d\n", sizeof(a + 0));//数组名不是单独使用,a+0表示首元素的地址,地址的大小就是 4/8
	printf("%d\n", sizeof(*a));//a表示首元素的地址,*a表示数组的首元素,求第一个元素的大小 4
	printf("%d\n", sizeof(a + 1));//a表示首元素的地址,a+1表示第二个元素的地址,求大小 4/8
	printf("%d\n", sizeof(a[1]));//a[1]表示数组第二个元素,求大小 4
	printf("%d\n", sizeof(&a));//&a表示整个数组的地址,求大小 4/8
	printf("%d\n", sizeof(*&a));//*&a 对整个数组的地址解引用,拿到整个数组,求大小 16
	printf("%d\n", sizeof(&a + 1));//&a+1表示跳过一个数组后的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0]));//&a[0]首元素的地址,求大小 4/8
	printf("%d\n", sizeof(&a[0] + 1));//&a[0]+1数组第二个元素的地址,求大小 4/8

3、一维字符数组 3.1 sizeof 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };
	printf("%d\n", sizeof(arr));//sizeod(数组名),所占内存大小。6个字符 ,求大小 6
	printf("%d\n", sizeof(arr + 0));//arr表示首元素的地址,arr+0表示首元素的地址,地址求大小 4/8
	printf("%d\n", sizeof(*arr));//arr表示首元素的地址,*arr取得首元素是一个字符,求大小 1
	printf("%d\n", sizeof(arr[1]));//arr[1]表示第二个元素,是一个字符,求大小 1
	printf("%d\n", sizeof(&arr));//&arr取整个数组的地址,地址求大小 4/8
	printf("%d\n", sizeof(&arr + 1));//&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8
	printf("%d\n", sizeof(&arr[0] + 1));//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8

3.2 strlen 练习 char arr[ ] = { ‘a’,‘b’,‘c’,‘d’,‘e’,‘f’ }
char arr[] = { 'a','b','c','d','e','f' };//数组中没有'//从数组首元素地址开始向后,一直到字符'printf'为止,'
	(
	"%d\n",strlen( ))arr;//数组的地址,求长度 随机值printf(
	"%d\n",strlen( +0arr ) );//arr首元素的地址,求长度 随机值//printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误
	printf
	(
	"%d\n",strlen( &))arr;//&arr整个数组的地址, 求长度 随机值printf(
	"%d\n",strlen( &+1arr ) );//&arr + 1移动整个数组的地址,指向数组末尾,还是地址,随机值,和上面差6printf (
	"%d\n",strlen( &[0arr]+1 ) );//arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,随机值和上面差1char[

3.3 sizeof 练习 char arr[ ] = “abcdef”
] arr="abcdef" ; //常量字符串,末尾隐藏字符'printf'("%d\n"
	,sizeof() );arr//sizeod(数组名),数组所占内存大小。6个字符 加上末尾隐藏字符'printf',求大小 7("%d\n",
	sizeof(+0 ))arr ; //arr不是2中例外,这里arr+0表示首元素的地址,求大小 4/8printf("%d\n",
	sizeof(*) );//arr表示首元素的地址,*arr取得首元素'a',求大小 1arrprintf("%d\n",
	sizeof([1 ])arr);//arr[1]表示第二个元素'b',求大小 1printf("%d\n",
	sizeof(&) );//&arr整个数组的地址,地址求大小 4/8arrprintf("%d\n",
	sizeof(&+ 1))arr ; //&arr+1移动整个数组的地址,指向数组末尾,还是地址,求大小 4/8printf("%d\n",
	sizeof(&[ 0]+arr1)) ; //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,求大小 4/8char[]=

3.4 strlen 练习 char arr[ ] = “abcdef”
"abcdef" arr;//常量字符串,末尾隐藏字符'printf' ( "%d\n",strlen
	()); //arr数组首元素的地址,求长度 6printfarr("%d\n",strlen
	(+0) );arr //arr首元素的地址,求长度 6 //printf("%d\n", strlen(*arr));//arr首元素的地址,*arr取得首元素'a',97,97作为一个地址,不能访问,类似野指针,错误//printf("%d\n", strlen(arr[1]));//第二个元素,错误printf("%d\n"
	,
	strlen
	(&)) ;//&arr整个数组的地址,数值等同首元素的地址 求长度 6printfarr("%d\n",strlen
	(&+1 ));arr //&arr + 1移动跳过整个数组的地址,指向数组末尾,还是地址,随机值 printf("%d\n",strlen
	(&[0 ]+1arr)); //arr[0]首元素,&arr[0]取首元素的地址,&arr[0] + 1第二个元素的地址,5 char*="abcdef";

3.5 sizeof 练习 char *p = “abcdef”
char [p ] ="abcdef"
等效于下面常见的代码,将字符串常量的首地址赋值给指针变量p
	; achar* = &;
	[ 0p ] =a*
	p(+0)=*p(+0)=[a0]char*a="abcdef";

printf (p "%d\n" ,sizeof
	()); //p是指针变量,保存首元素地址,地址求大小 4/8printfp("%d\n",sizeof
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求大小 4/8 printf("%d\n",sizeof
	(*)) ;//*p取出首元素 'a',求大小 1printfp("%d\n",sizeof
	([0] ))p;//p[0]代表首元素 'a',求大小 1printf("%d\n",sizeof
	(&)) ;//&p 是指针变量p在内存中的地址, 地址求大小 4/8printfp("%d\n",sizeof
	(&+1 ));p //4/8 - &p+1是跳过p之后的地址,地址求大小 4/8 printf("%d\n",sizeof
	(&[0 ]+1p)); //4/8 &p[0]是‘a’的地址,&p[0]+1就是b的地址,地址求大小 4/8 char*="abcdef";

3.6 strlen 练习 char *p = “abcdef”
printf (p "%d\n" ,strlen
()); //p是指针变量,保存首元素地址,求长度 6printfp("%d\n",strlen
	(+1) );p //p+1,指针指向第二个元素'b'的地址, 求长度 5 //printf("%d\n", strlen(*p));//*p取得首元素 'a' ,97,内存中97这个地址不能访问,类似野指针//printf("%d\n", strlen(p[0]));//p[0]得到首元素 'a',97,内存中97这个地址不能访问,类似野指针printf("%d\n"
	,
	strlen
	(&)) ;//&p 是指针变量p在内存中的地址, 求长度 随机值printfp("%d\n",strlen
	(&+1 ));p // &p+1是跳过p之后的地址, 求长度 随机值  printf("%d\n",strlen
	(&[0 ]+1p)); // &p[0]是首元素‘a’的地址,&p[0]+1就是b的地址,求长度 5 int[3][

4、 sizeof 二维整形数组 int a[ ][4] = { 0 }
4 a]=0};printf ( { "%d\n" ,sizeof
	()); //sizeof(a)求取整个数组的大小,48printfa("%d\n",sizeof
	([0] [0a]));//(a[0][0]是第一行第一个元素,求大小 4printf("%d\n",sizeof
	([0] ))a;//a[0]代表二维数组首元素,即第一行数组的数组名,sizeof(a[0])求第一行数字的大小 16printf("%d\n",sizeof
	([0] +1a)); //a[0]第一行数组的数组名,没有放在sizeof里面,没有单独取地址,因此,a[0]代表第一行数组第1个元素的地址,a[0] +1是第一行数组第二个元素的地址,求大小 4 printf("%d\n",sizeof
	(*([ 0]+1a))) ; //解引用取出第一行第二个元素,求大小 4printf("%d\n",sizeof
	(+1) );a //a不是两个例外,表示二维元素的首元素地址,a+1表示第二个元素的地址,就是第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(+ 1)))a ; //*(a + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(&[0 ]+1a)); //&a[0]第一行数组的地址,&a[0]+1 表示第二行数组的地址,求大小 4 printf("%d\n",sizeof
	(*(& [0]+1a))) ; //*(&a[0] + 1)取出第二行数组,求大小 16printf("%d\n",sizeof
	(*)) ;//a为首元素地址,*a取出首元素的内容,即第一行数组, 求大小 16printfa("%d\n",sizeof
	([3] ))a;//地址,a[3]也是int[4] 类型,里面的元素都是随机数值,求大小 16



总结

本文先复习了一些知识点,尤其是二维数组,要牢记数组名的一般情况和两个例外,通过sizeof 和 strlen 的练习,再次复习了数组和指针的知识点。

这段时间所学知识都是建立在前面的基础之上,知识不牢,地动山摇,要经常对前面所学的知识点进行复习。

若有地方总结错误,也请大家友好指正,谢谢大家! 下一篇继续更新数组和指针的练习。

欢迎分享,转载请注明来源:内存溢出

原文地址: https://www.outofmemory.cn/langs/707584.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-04-24
下一篇 2022-04-24

发表评论

登录后才能评论

评论列表(0条)

保存