我称自己为“浦哥”,因为我可能比大多数读者都年长。它重点关注C 语言的三个核心:数组、指针和函数,从某种意义上说,您可以信任人们与您一起做事。今天继续写技术文章。
上次写C语言数组的时候,有的书先解释指针,有的书先解释函数。根据我目前为止学习C语言的顺序以及我对C语言的理解,学习顺序如下。数组---指针---函数本文介绍C 指针。
C是一门值得学习的语言,是它让我进入编程的语言,它的许多编程思想至今仍然影响着我,帮助着我的工作。
基本概念
要学习C语言中的指针,我强烈推荐以下书籍:《C 和指针》 如果你彻底阅读这本书,你将会擅长C语言指针。
1、
指针有两个元素
(1)首地址:内存中连续字节的第一个字节的编号。在32位系统上,每个字节数都是32位二进制,任何类型的指针都只有4B。空间被占用。
1 个字符*a;
2 短*b;
3int *c; int* c;
4 双*d;双*d;
五
6printf('%d %d %d %d\n', sizeof(a), sizeof(b), sizeof(c), sizeof(d));
在7//32 位系统上,结果是4 4 4 4。这就证明只要是指针,其实就是4B。简单地代表数字的内存。
(2) 指针所指向的空间的数据类型:从指针的值开始所指向的空间的数据类型。
2、
指针类和值类
到目前为止您所学到的各种数据类型(int、float 等)统称为值类。
指针类和值类不能简单地应用上述语法。例如,自动类型转换或强制不能应用于指针类。
3.
基本指针操作
和*
A。
:地址运算符,一元运算符。它在一元运算符中的优先级相对较低,低于++和--。
一个左值(左值只能是空格或变量)占用一个内存地址。
常量和表达式语法不正确。
1 3. (n) 和n 都是错误的形式。
B.
1短i、j、*p、*q、**r;
2//两个值类变量:i和j,三个指针类变量:p,q,r
3//p和q是指针变量,它们指向的数据类型是:
4//r是指针变量,但是r指向的空间的数据类型是short *
5//对于指针指向的数据类型:去掉最后一个'*',剩下的部分和类型成为内容。
6
7//p=i 正确,所以将变量/空间i的地址赋给p。
8//r=i;不正确。指针在进行赋值操作之前,必须保证左右两侧的数据类型相同。 r的数据类型是short **,i的数据类型相同。分配失败,因为:短*
9//r=p;是正确的。 r 指p。首先,我们需要明确这些指针的数据类型和指向空间的数据类型之间的对应关系。
C。
* 操作员
一元运算符具有相同的优先级,并且是彼此相反的运算(两个连续的和* 运算符一起相互抵消)。例如,*n=n,*p=p。
语法:*指针(常量、变量、表达式)
1短i、j、*p、*q、**r;
2p=我;
3q=j;
4*p=30; //将30赋给“p指向的空间”,即i这相当于i=30。
5*q=*p + 15; //将p和15指向的空间中的值相加,并将和赋给q指向的空间。这相当于j=i + 15。
*一些理解:
(1)式在左边,理解为:
(2) 在表达式中,理解为指定空间的值。
1短i、j、*p、*q、**r;
2p=我;
3q=j;
4r=p;
5*p=**r + *q; //将r指向的空间的值和q指向的空间的值相加,并赋值给指向的空间。 p,相当于i=i + j。
四。
理解指针定义
A。
1char i, j, *p=i, *q=j, **r=p;
2//定义语句中的*不是指向运算符,它只是一个指针标识语句。
B.
双*p;
*p=3.14;
理解上面这句话很重要。
上面的语句将导致运行时出现致命错误。
变量p被定义为指针变量,占用4B,但未初始化(没有赋初值),其值为垃圾数据。
*p=3.14;表示将3.14赋值给p指向的空间,即把3.14赋值给首地址指向的空间,以p的值作为首地址。
总结一下,我们将3.14分配给以垃圾值开头的地址所指向的空间。只有魔鬼知道这个空间在哪里。这个垃圾值的范围是0 到40 亿,如果它在你当前软件强制的空间范围内,那么一切都很好。否则,此操作(*p=3.14;) 将影响该空间。如果您操作不属于本软件的应用程序空间,操作系统将视为“未经授权的访问”,并强制终止本软件的执行。
五。
对指针的其他操作(主要是指针加法和减法)
指针对整数值进行加/减,结果是一个指针,它所指向的空间类型不会改变。
A。
指针加减整型
P+1:得到的仍然是一个指针,指向P所指向的空间中的下一个地址(移动到下一个地址的长度就是该空间中指向的数据类型的长度)。
指针“字节数”的值+1。与指针原始值(原始字节数)的差异是sizeof(指向空间的数据类型)。
指针+n 的值与原始指针的值相差n 倍sizeof(所指向空间的数据类型)。
B.
指针减指针=int类型
指针减去指针的结果的绝对值是两个指针所指向的空间之间的sizeof(数据类型)元素的数量。
参与指针减法运算的两个指针必须具有相同的指向空间的数据类型。
本质上,指针减法的内部运算过程如下:减去两个指针值(以字节为单位)并除以sizeof(它们指向的空间的数据类型)。
您不能将指针添加到指针。出现语法错误。
概要:指针+1或-1,指针移动的步长:指向的空间数据类型的长度(这个长度可以通过sizeof()计算)
指针与数组
1.
指针和一维数组
整数a[10];
数组名的本质:数组的首地址常量。
A.数组名是一个常量
1int a[10], *p=a[0];
2++a; //错误!++操作的本质是赋值常量不能被赋值。 a 是数组的名称。
3++p; //指针变量
B.
数组名是首地址(指针),可以参与指针可以参与的所有操作。
1*a=3; //a的值本质上是a[0]的首地址,所以我们可以说:a指向a[0]
2*(a+0)=3;=a[0]=3;
3*(a+1)=3;=a[1]=3;
4*(a+2)=3;=a[2]=3;
int i; //该值在有效下标范围内。
*(a+i)=3; a[i]=3;
理解指针和数组的本质。
a[i]=*(a+i)
外观的本质
2、
指针和二维数组
理解指针和二维数组只是比较,如果你想理解指针和二维数组,那么指针和多维数组、三元指针、四元指针、五元指针,甚至多维指针就变得很难针对了。序数指针、一维数组和二维数组一维、三维、甚至多维数组只有深入挖掘其本质才能理解。
指针和二维数组是指针的进一步演变。稍后我会分享这些知识。
指针和字符串
1、
'ABCDE' //字符串常量
字符串常量的本质:它是字符串的首地址常量,或者说是指针常量。
1char *p='我爱你';
2
3p=“你好”;
4printf('%s\n', p);
5p[2]='m'; //错误,无法分配字符串常量。
2、
字符串常量本质上是指针常量,可以参与指针可以参与的所有操作。
所以:
字符串常量可以执行*和[]操作。
不能添加字符串常量(不能添加指针)。
字符串常量上的关系运算符(大小比较)实际上比较第一个内存地址的大小,而不是字符串内容(ASCII 代码)的大小。
字符串常量不能更改其内容。
字符串的本质是字符数组,数组名的本质仍然是指针常量。
因此,上述结论也适用于字符串。
3.
String类处理函数
A。
字符串.h
了解scanf('%s'.) 和gets()
strlen() 函数的工作原理:
C语言将其唯一的参数视为首地址,并从该首地址指向的空间开始计算所有字符,直到达到0(结束标志)。
B.
字符串输入/输出函数
输入:scanf('%s',), gets(.)
输出: printf('%s',), puts(.)
C。
strcpy()
语句: char *strcpy(char *target, char *source);
功能:将后一个字符串赋值给前一个字符串。将第二个参数的值复制到从地址指向的字节开始的“停于零”字符,并将其分配给第一个参数的值。如果首地址在向后连续的存储空间中,则该函数的返回值为第一个参数的值。
D .
strcat()
语句: char *strcat(char *, char *);
特点:字符串连接。将第二个参数指定的字符串连接到第一个参数指定的字符串的末尾。
E.
strstr()/strchr()
语句: char *strstr(char *string, char *subString);
//subString含义:子字符串
功能:查找地址值中第一次出现的subString。如果subString 不是string 的子字符串,则返回NULL。
F。
strcmp()
语句:int strcmp(char *s1, char *s2);
功能:比较s1和s2指向的字符串的内容。
如果s1 字符串的内容小于s2 字符串的内容,则返回值为负整数。
如果s1 字符串的内容大于s2 字符串的内容,则返回值为正整数。
如果两个内容相等则返回0。
G。
strrev()
语句: char *strrev(char *);
功能:反转字符串。
本文只是对C语言指针的介绍。我不确定读完这篇文章你能理解和学到多少,但是你只有通过更深入的思考才能学会C指针。你能消化并理解吗?
版权声明:本文由今日头条转载,如有侵犯您的版权,请联系本站编辑删除。