【C语言进阶学习笔记】二、指针的进阶(1)(重点必看+代码图解+练习)

本文深入探讨C语言中的指针进阶知识,包括字符指针的使用,指针数组的概念,以及数组指针的定义和使用。通过实例分析了字符指针如何存储字符串首地址,以及数组参数和指针参数的传递方式。文章强调了常量字符串在内存中的特性,并提醒读者注意指针类型和数组的关系,以及在使用中应注意的细节。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在C语言基础阶段,我们学习过指针相关的一些基础内容,比如说:

1.指针是一个变量,用来存放地址,地址是唯一标识一块内存空间
2.指针的大小是固定的4 / 8个字节(32位平台 / 64位平台)
3.指针是由类型,指针的类型决定了指针的 + -整数的步长,指针解引用操作时候的权限
4.指针的运算

本篇文章及后面的几篇文章将会更加详细的去介绍和学习指针的进阶部分。(指针的内容在数据结构中会经常用到,所以一定要好好学习,打好基础~)
在这里插入图片描述



1、字符指针

在指针的类型中我们知道有一种指针类型为字符指针char*;
一般使用方式:
在这里插入图片描述

这种方式通过字符指针解引用改变原字符变量的内容。
实际上,字符指针也可以这样使用:
在这里插入图片描述

这种方式是将字符串的首地址放到指针中,通过指针可以找到该字符串(千万不要理解成将字符串放到指针里面去,这是不可能的)。(类似与数组名就是首元素地址,但是跟数组还是有所区别的,这个字符串是一个常量字符串,无法被改变,如下图:)

在这里插入图片描述


如果说我们想修改这个字符串,需要将其放入数组中,然后再去修改:
在这里插入图片描述
扩展:在C语言中,内存可以被划分为栈区、堆区、静态区、常量区。
在这里插入图片描述

栈区:局部变量,函数形参,函数调用
堆区:动态内存如malloc等申请使用
静态区:全局变量,static修饰的局部变量
常量区:常量字符串
常量区中的内容在整个程序的执行期间是不允许被修改的,且同一份常量字符串只会创建一份,不会重复创建存储。


请看以下代码,猜猜输出结果是什么?

#include<stdio.h>
int main()
{
   
	char arr1[] = "abcdef";
	char arr2[] = "abcdef";
	char* p1 = "abcdef";
	char* p2 = "abcdef";
	if (arr1 == arr2)
	{
   
		printf("arr1 == arr2\n");
	}
	else
	{
   
		printf("arr1 != arr2\n");
	}
	if (p1 == p2)
	{
   
		printf("p1 == p2\n");
	}
	else
	{
   
		printf("p1 != p2\n");
	}
	return 0;
}

在这里插入图片描述

分析:

创建数组需要开辟空间,数组arr1和arr2在内存空间所在位置是不同的,所以arr1 != arr2; char* p1 = “abcdef”; char* p2 = “abcdef”; "abcdef"是常量字符串,不能被修改,在内存空间所占位置固定,char * p1 = “abcdef”; 是将该常量字符串的首地址放到字符指针p1中,char* p2 = “abcdef”;
是将该常量字符串的首地址放到字符指针p2中。也就是说p1和p2存放都是常量字符串"abcdef"的首地址,所以 p1 ==p2。(注意:同样的常量字符串只会存一份,不会同时存两份,所以不会开辟不同的空间来存储。)

在这里插入图片描述

char* p2 = “abcdef”; 这种写法本身也不严谨,严谨的写法应该是:
const char* p2 = “abcdef”; (指向常量字符串的指针最好加上const!)

总结:这里arr1和arr2指向的是一个同一个常量字符串。
C /C++会把常量字符串存储到单独的一个内存区域当几个指针。指向同一个字符串的时候,他们实际会指向同一块内存。但是用相同的常量字符串去初始化不同的数组的时候就会开辟出不同的内存块。所以arr1和arr2不同,p1和p2相同。


2、指针数组

指针数组是一个存放指针的数组

int* arr1[5];
char* arr2[5];
double* arr3[5];

整型数组-- - 存放整型的数组

int arr4[10];

字符数组-- - 存放字符的数组

char arr5[10];

看以下代码,猜猜结果是什么?

#include<stdio.h>
int main()
{
   
	int a = 10;
	int b = 20;
	int c = 30;
	int* arr[3] = {
    &a, &b, &c };
	int i = 0;
	for (i = 0; i < 3; i++)
	{
   
		printf("%d ", *arr[i]);
	}
	return 0;
}

在这里插入图片描述


我们知道数组名可以代表首元素的地址,请看下面这段代码:

#include<stdio.h>
int main()
{
   
	int arr1[] = {
    1,2,3 };//arr1--int*
	int arr2[] = {
    4,5,6 };//arr2--int*
	int arr3[] = 
评论 17
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

大家好我叫张同学

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值