一,一维数组
1,定义:vs不会自动初始化;
初始化:int arr[10]={0};
剩余元素全为0: int arr[10] = {1,2,3};
2.数组名为首元素地址;
3.数组的存放是连续的,由低地址到高地址;
注意:变量代码写的时候是由高地址到低地址;
二,二位数组
1.初始化:int arr [3] [4]={0};
剩余元素全为0: int arr[3] [4]= {1,2,3};
int arr[3] [4]= {{1},{2},{3}}:1,2,3在第一列;
注意:二维数组行可以省略,列不能省略;int [] [4];
2,数组名为第一行数组地址;
3.二维数组就是一个一级指针数组;
三.指针数组
1.存放指针的数组;
int* p [10];(因为*的优先级为四级,[]的优先级为1,所以p先和[]结合)
四,存放数组指针的数组
1,数组指针:首先它是一个存放数组地址的指针变量;
如:int arr[5]={0};
int (*p)[5]=arr;(p先和*结合,为指针,[5]表示为存的数组有5个元素;它的类型为int (*)[5])
2,数组指针数组
如:int(*p[3])[5];因为p先和[]结合,所以确定他是一个数组,是可存放三个int (*)[5]类型的元素;
注意:他也可以来存放二维数组;
五.存放函数指针的数组
1.函数指针:存放函数的地址的指针;
如:void (*p)(int ,int)=add,p为指针变量,存放void ()(int,int)类型的函数的地址
函数地址:函数名就是函数地址;&add=add;
2.函数指针数组:毫无疑问,他是一个数组
如:void(*p[4])(void(*)(char,char),int)存放4个void(*)(void(*)(char,char),int)类型的函数指针;
六,数组传参(传参是数组会退化成指针)
1.一维数组传参:方法一:int p(int arr[]),[]内是否有数字,以及数字的大小都不会影响,并且没作有;
方法二:int p (int *p);
其实传过来的都是数组首元素地址,并不会真正创建数组;
2.二维数组传参:
方法一:int p(int arr [] [])
方法二:int p(int (*arr)[5]);传过来一个数组指针,也就是第一行元素的地址;
(二维数组的数组名等于第一行元素的地址)
3.一级指针传参&二级指针传参&函数传参
七.一维数组在sizeof和strlen
int arr[5]={0,1,2,3,4};
1.sizeof(arr)=30;(只有sizeof(arr)和&arr时arr代表整个数组)
sizeof(arr+0)=4/8;
sizeof(*arr)=4;
sizeof(&*arr)=30;
2.strlen(arr)=随机值(因为strlen在碰到/0才会停止,此处arr为首元素地址);
八.二维数组在sizeof和strlen
int arr[3][4];
a[0]=>第一行元素的数组名=>第一行第一个元素的地址,只有sizeof(arr[0])和&arr[0]时arr代表整个数组;
1.sizeof(a[0])=16
sizeof(a[0]+1)=sizeof(&a[0][1])=4/8;
sizeof(a+1),a没有单独放,所以a是第一行元素地址,+1就是第二行元素地址;
sizeof(*(a+1)),对第二行元素解引用,得到第二行数组名,因为单独放,所以等于16;
sizeof(&a[0]+1)=4/8;&a[0]代表第一行元素地址,+1就是第二行元素地址;