数组
1、int a[];不可以,要制定分配空间
2、scanf("%d",n);
int a[n];
不可以
3、置零:int a[10] = {0};
4、数组名指针常量,保存的是元素的首地址,元素首地址不可修改
数组的地址
1、int main()
{
int i;
int *p;
int a[5];
p = a;
for(i= 0; i < 5; i++)
{
scanf("%d",p + i);
}
for(i= 0; i < 5; i++)
{
printf("%d",*(p + i));
}
}
此程序没有问题,因为p的值并没有改变,当为p++时,才需要p = a;
此外,输入时候scanf("%d",&p[i]);也可以
2、一维数组:
int a[3];
printf("%p",a);
printf("%p",&a);
这两个输出的结果是一样的
printf("%p",a);
printf("%p",&a+1);
但这两个的结果不是一样的,一个加4一个加12;
原因分析:
因为&a为数组的地址,所以步长为12(即整个数组的长度),a为数组首元素的地址,步长为4;
数组指针
举例:#include <stdio.h>
#define MAX_SIZE 5
int main()
{
int i;
int (*p)[5]; //定义形式
int str[MAX_SIZE];
p = &str; //初始化,数组指针存放的是数组的地址
for(i = 0; i < 5; i++)
{
//scanf("%d",*p + i);
scanf("%d",&((*p)[i]));
}
for(i = 0; i < 5; i++)
{
//printf("%d\t",(*p)[i]); //因为 p = &str,变量替换
printf("%d\t",*(*p + i));
}
printf("\n");
return 0;
}
其中:sizeof(p) = 4;
总结:1、&a:对一维数组取地址等于数组的地址
2、*(&a):对一维数组的地址取值等于一维数组首元素的地址
二维数组
#include <stdio.h>#define MAX_SIZE 2
int main()
{
int i;
int j;
int a[MAX_SIZE][MAX_SIZE];//定义时可以 省略行,不可以省略列
for(i = 0; i < MAX_SIZE; i++)
{
for(j = 0; j < MAX_SIZE; j++)
{
//scanf("%d",&a[i][j]);
scanf("%d",*(a + i) + j);
}
}
for(i = 0; i < MAX_SIZE; i++)
{
for(j = 0; j < MAX_SIZE; j++)
{
//printf("a[%d][%d] : %d\t",i,j,a[i][j]);
printf("a[%d][%d] : %d\t",i,j,*(*(a + i) + j));
}
}
printf("\n");
return 0;
}
二维数组的单位为一维数组,所以二维数组名为第一个一维数组的地址。
分析:*(*(a + i)+ j)
a+i : a为第一个一维数组的地址,a+i为第i个一维数组的地址
*(a + i):第i个一维数组首元素的地址
*(a + i)+ j:第i个一维数组的第j个元素的地址
*(*(a + i)+ j):第i个一维数组的第j个元素的值
*(&a):第一个一维数组的地址
**(&a)):第一个一维数组的首元素的地址
***(&a)):第一个一维数组的首元素的值
拓展:三维数组
#include <stdio.h>int main()
{
int a[3][2][2] = {1,2,3,4},{5,6,7,8},{9,10,11,12};
//三维数组第一个是二维数组的个数,第二个和第三个为二维数组的行列
}
那么:*(*(*(a + i)+ j)+ k):a + i为第i个二维数组的地址,*(a + i)为为第i个二维数组的第一个一维数组的地址,*(a + i)+ j为第i个二维数组第j个一维数组的地址,*(*(a + i)+ j)为第i个二维数组第j个一维数组的首元素的地址,*(*(*(a + i)+ j)+ k)为第i个二维数组第j个一维数组的第k个元素的值
数组指针的作用
#inlcude <stdio.h>void func(int a[5])
{
printf("%d",sizeof(a));
}
int main()
{
int a[5] = {1,2,3,4,5};
printf("%d",sizeof(a));
}
主函数的值为20,调用函数的值为4,因为当数组名做函数形参时自动转化为int *a;此时a的大小为指针的大小,这时a可以在调用函数中做自加运算,因为此时他已经是一个指针变量。
#inlcude <stdio.h>
void func(int **a)
{
int i;
intj;
for(i = 0; i < 2; i++)
{
for(j = 0; j < 2; j++)
{
printf("%d",*(*(a + i) + j));
}
}
}
int main()
{
int a[2][4] = {1,2,3,4};
func(a);
}
不行,指针不兼容
指针不兼容的根本原因是步长不一样,传过去的实参a的步长为8,而形参的步长为4,
这时可以将形参定义为数组指针:int (*p)[2],此时的步长相同,也验证了实参是一维数组的地址,就要用一维数组指针来接
argv与argc
命令行传参数#include <stdio.h>
int main(int argc, char *argv[])
{
printf("argc = %d\n",argc);
int i;
for(i = 1; i < argc; i++)
{
printf("argv[%d] = %s\n",i,argv[i]);
}
return 0;
}
运行(Linux环境):
[root@localhost 1226]# ./a.out hello1 hello2 hello3
argc = 4
argv[1] = hello1
argv[2] = hello2
argv[3] = hello3