C语言指针——指针与数组

数组参数是指针

函数参数列表很多时候会传进去数组的参数,那传入的数组究竟是什么呢?
我们可以做点实验看看
有这样一段程序求一个数组中的最大和最小值

#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的指针了,

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值