数组参数是指针
函数参数列表很多时候会传进去数组的参数,那传入的数组究竟是什么呢?
我们可以做点实验看看
有这样一段程序求一个数组中的最大和最小值
#include<stdio.h>
void minmax(int a[], int len, int *max, int *min);
int main(){
int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int min,max;
minmax(a, sizeof(a)/sizeof(a[0]), &max, &min);
printf("min = %d, max = %d", min,max);
return 0;
}
void minmax(int a[], int len, int *max, int *min){
int i;
*min = *max =a[0];
for(i =1; i<len; i++){
if(a[i]<*min){
*min = a[i];
}
if(a[i]>*max){
*max = a[i];
}
}
}
传入minmax函数的数组a[],没有指定大小那究竟是什么呢?
我们可以分别sizeof(a)一下可以得到
#include<stdio.h>
void minmax(int a[], int len, int *max, int *min);
int main(){
int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int min,max;
printf("main sizeof(a) = %lu\n",sizeof(a));//main函数的中数组a[]的sizeof
minmax(a, sizeof(a)/sizeof(a[0]), &max, &min);
printf("min = %d, max = %d\n", min,max);
return 0;
}
void minmax(int a[], int len, int *max, int *min){
int i;
printf("minmax sizeof(a) = %lu\n",sizeof(a));//minmax函数的中数组a[]的sizeof
printf("main sizeof(a) = %lu\n",sizeof(a));
*min = *max =a[0];
for(i =1; i<len; i++){
if(a[i]<*min){
*min = a[i];
}
if(a[i]>*max){
*max = a[i];
}
}
}
输出显示一下
main sizeof(a) = 40
minmax sizeof(a) = 4
min = 1, max = 10
在minmax函数中sizeof(a)=4,这个4是什么呢?
另外运行这段程序会有一个警告
warning: 'sizeof' on array function parameter 'a' will return size of 'int*'
意思是参数列表中数组a的sizeof返回的是int*的大小也就是整型指针的大小,那这是不是就说明函数参数表中的数组其实就是一个指针呢?
为了验证这个想法我们来输出一下main函数和minmax函数中数组a的地址
#include<stdio.h>
void minmax(int a[], int len, int *max, int *min);
int main(){
int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int min,max;
printf("main sizeof(a) = %lu\n",sizeof(a));
printf("main a = %p\n",a);//main函数中数组的地址
minmax(a, sizeof(a)/sizeof(a[0]), &max, &min);
printf("min = %d, max = %d\n", min,max);
return 0;
}
void minmax(int a[], int len, int *max, int *min){
int i;
printf("main sizeof(a) = %lu\n",sizeof(a));
printf("minmax a = %p\n",a);//minmax函数中数组的地址
*min = *max =a[0];
for(i =1; i<len; i++){
if(a[i]<*min){
*min = a[i];
}
if(a[i]>*max){
*max = a[i];
}
}
}
main sizeof(a) = 40
main a = 0061FEF8
main sizeof(a) = 4
minmax a = 0061FEF8
min = 1, max = 10
可以看到main函数和minmax函数中a的地址是一样的,也就是说main函数中的数组a和minmax函数中的数组a是一个数组,那么也就是函数参数列表中的数组其实是一个指针。
那既然是个指针那么我们可以将参数改成指针看一下
#include<stdio.h>
void minmax(int *a, int len, int *max, int *min);
int main(){
int a[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
int min,max;
printf("main sizeof(a) = %lu\n",sizeof(a));
printf("main a = %p\n",a);
minmax(a, sizeof(a)/sizeof(a[0]), &max, &min);
printf("min = %d, max = %d\n", min,max);
return 0;
}
void minmax(int *a, int len, int *max, int *min){//将数组改成指针
int i;
printf("main sizeof(a) = %lu\n",sizeof(a));
printf("minmax a = %p\n",a);
*min = *max =a[0];
for(i =1; i<len; i++){
if(a[i]<*min){
*min = a[i];
}
if(a[i]>*max){
*max = a[i];
}
}
}
main sizeof(a) = 40
main a = 0061FEF8
main sizeof(a) = 4
minmax a = 0061FEF8
min = 1, max = 10
可以看到输出结果是一样的,甚至之前的那个警告都消失了。也证实了之前的说法。
数组变量是特殊的指针
以下函数原型是一样的
int sum(int *ar, int n);
int sum(int ar[], int n);
数组变量本身表达地址
int a[10]; int *p = a;//无需用&取地址
a == &a[0];
但是数组的单元表达的是变量,需要用&取地址
[ ]运算符可以对数组做,也可以对指针做
p[0] == a[0];//把指针所指的地方当作一个数组
*运算符可以对指针做也可以对数组做
数组变量是const的指针,所以不能被赋值
int a[] <==> int * const a
指针与const
指针是const
表示一旦得到了某个变量的地址,不能在指向其他变量
int * const q = &i;//q是const
*q = 26;//ok
q++;//error
所指是const
表示不能通过这个指针去修改那个变量(并不是使得那个变量成为const)
const int *p = &i;
*p = 26;//error (*p)是const
i = 26;//ok
p = &j;//ok,指针还可以指向其他变量
这些是什么意思?
int i;
const int *p = &i;//1
int const *p = &i;//2
int *const p = &i;//3
const与指针只有两种关系要么通过指针不能修改,要么指针不能修改
判断哪个被const的标志是const在*前面还是后面,所以1==2
const数组
const int a[] = {1, 2, 3, 4}
表示数组变量已经是const的指针了,