C语言指针和数组

本文详细介绍了C语言中的数组和指针概念。数组是一系列相同类型元素的集合,可以通过下标访问。指针则存储了变量的地址,数组名实际上是首元素的地址。在函数调用中,数组名会被解释为指向数组首元素的指针。文中还探讨了数组的初始化、常量数组、指针运算以及在函数参数中的使用。此外,提到了如何通过const关键字保护数组内容不变,并介绍了多维数组和指向多维数组的指针的表示方式。
摘要由CSDN通过智能技术生成

数组

数组由一系列类型相同的元素构成,数组声明中包括数组元素的数目和元素的类型。

int main() {
	float candy[365];
	int arr[3]={1,2,3}; //数组初始化:只有初始化的时候才可以这样赋值
	int arr[3]={[2]=1}; //指定初始化第三个数为1
	arr={1,2,3};//不起作用
}
  • 方括号[]表示candy为数组,方括号内的数字指明了数字所包含的元素数目。
  • 如果要访问数组元素,可以使用下标数字来表示单个元素。下标数字也称索引,从0开始计数。

只读数组:数组中的每个元素都是常量,需要在声明时进行初始化,因为声明之后,不可以再对它赋值。

const int arr[3] = {1,2,3};

指针

指针提供了一种用来使用地址的符号方法。数组标记实际上是一种变相使用指针的形式。

数组名同时也是该数组首元素的地址。(常量)
int arr[3] = {1,2,3};
arr == &arr[0]; //数组名是该数组首元素的地址
arr, &arr[0] 都代表首元素的内存地址,两者都是常量,可以将其作为赋给指针变量的值。

在C中,对一个指针加1的结果是对该指针增加一个存储单元,对于数组而言,地址会增加到下一个元素的地址,而不是下一个字节。
在这里插入图片描述
声明指针时必须声明它所指向对象的类型,因为计算机需要知道存储对象所用的字节数,指针自增和自减时与字节数有关。

  • 指针的数值就是它所指向的对象的地址。地址的内部表现方式是由硬件来决定的。
  • 在指针前运用运算符*就可以得到该指针所指向的对象的数值。
  • 对指针加1,等价于对该指针的值加上它指向的对象的字节大小。
    dates + 2 == &date[2]; //相同的地址,dates+index是元素date[index]的地址。
    *(dates + 2) == dates[2]; // 相同的值

函数,指针和数组

可以在指针符号中使用数组名,也可以在数组符号中使用指针。

//第一个参数是数组的地址,第二个参数是数组长度
int sum(int *ar,int n){
	int total = 0;
	for(int i = 0;i < n;i++)
		total += ar[i]; 
	return total;
}

只有在函数原型或者函数定义头的场合中,可以用int *ar代替int ar[]。无论在任何情况下,形式int *ar都表示ar是指向int的指针。int ar[]可以表示ar是指向int的指针,但是只是在声明形式参量时才可以使用。使用第二种形式可以提醒读者ar不仅是指向一个int数值,而且它指向的这个int是一个数组中的元素。

正常定义的数组,其数组名存储的是数组第一个元素的地址,是一个常量,赋值或者自增自减运算不合法。

把一个定义好的数组作为函数的形参时,此时数组名在编译时就会被当作指针变量来处理(形参肯定是一个指针变量,只有指针变量才能存放地址),此时这个形参的赋值或者自增自减运算是合法的。

以指针传进去,而指针是一个地址变量,可以进行操作。
在这里插入图片描述

指针变量的操作

  • 赋值int *p = &a
  • 求值 int a = *p
  • 取指针地址int **q = &p
  • 将一个整数加给指针,这个整数都会和指针所指类型的字节数相乘,然后所得的结果会加到初始地址上,如果相加的结果超出了初始指针所指向的数组范围,那么这个结果是不确定的。

保护数组内容

在处理普通变量时,可以进行值传递,不改变原本的值。对于处理数组的函数,只能传递指针,原因是这样能使程序的效率更高,如果通过值向函数传递数组,那么函数中必须分配足够存放一份原数组的拷贝的存储空间,然后把原数组的所有数据赋值到这个新数组中,效率不够高。

如果我们不希望修改该数组的值,可以用const
int sum(const int ar[],int n);//函数声明
此时数组的值无法修改。

指针和多维数组的关系

int arr[4][2];
数组名arr是数组首元素的地址,首元素包含了两个int的数组,因此arr也是包含两个int的数组的地址。

  • arr=&arr[0], arr[0]=&arr[0][0],
  • arr+1 下一行,arr[0]+1,下一个
  • arr[0]是首元素arr[0][0]的地址,所以*arr[0] == arr[0][0], *arr = &arr[0][0], **arr = *&arr[0][0] = arr[0][0].

图中的arr作为指针使用
在这里插入图片描述

定义指向多维数组的指针

int (* pz)[2]; pz指向一个包含两个int值的数组。[]的优先级高于*,如果不加括号,那么定义的就是由两个指针组成的数组。

参考《c primer(第五版)》

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值