C语言知识点之 指针1

简介: C语言知识点之 指针1

导言

今天分享一些C语言指针的基础知识

1.指针是什么

a

指针是内存中最小单元的编号,也叫做地址

b

指针通常指的是指针变量,是用来存放地址的变量

注意:

存放在指针变量里的数值,在处理时默认是地址

概念辨析:

a

内存被划分为很多内存单元,每个内存单元大小是一个字节

b

每个字节的内存单元都有一个唯一的编号

c

地址是不需要存储起来的,如果要存储的话,要放在指针变量里。

在32位机器中,地址大小是(32个bit位)4个字节,所以指针的大小也是4个字节

在64位机器中,则是8个字节(64个bit位)

2.指针和指针类型

即然在同一个机器下地址大小是固定的,那么为什么还要有不同类型的指针呢

作用a:

下面给出一组对比

由此可以看出:

指针类型决定了指针进行解引用操作的时候,访问几个字节。

int* 访问四个字节

char*访问一个字节

区别b :

给出另一组对比

在进行运算时,都是+1

char*,只增加1个字节

int*则会增加4个字节

由此可以看出,其增加的是其类型的字节大小。

所以,要达到相同的目的,不同的指针类型所需要的次数也不同

3.野指针

指针指向的位置是不可知的,即其指向的不是自己

3.1野指针成因

a 指针未初始化

int *p;//直接报错

b 指针越界访问

c 指针的空间被释放

简单解释一下:

尽管p在函数中接收了a的地址,但a这个临时变量其在内存中申请的空间已经随着函数的结束而销毁了,所以p就是一个野指针

3.2避免形成野指针

a 指针初始化

如果明确知道指针指向的对象,那就初始化地址即可

如果指针不知道初始化什么值,为了安全,此时可以将其初始化为NULL(空指针),用这个方法可以处理3.1.c的问题

注意:

地址是NULL(0)时,是无法访问的

b 小心指针越界

c 避免返回局部变量的地址

d 指针使用之前要检查其有效性

4.指针运算

4.1指针与整数

可以参考2.b的运算

提示:

[]仅仅是操作符:

所以arr[i] == i[arr]

因为在编译时,上面两个表达式都会转换为*(arr+i),并且数组在内存中的存储是连续的

4.2指针与指针

指针-指针的前提:

两个指针指向同一块区域。

其差值的绝对值是他们之间的元素个数

应用:模拟strlen求字符串长度

#include<stdio.h>
size_t my_strlen(char* str)
{
  char* start = str;
  while (*str)//当str解引用后不是“\0”的时候,就一直循环
  {
    str++;
  }
  return str - start;
}
int main()
{
  char arr[] = "abcdef";
  size_t len = my_strlen(arr);
  printf("%zd\n", len);
  return 0;
}

4.3指针的关系运算

请观察下面在for循环中两种指针的关系运算

代码1:

#define VA 5
float values[VA];
float* vp;
int main()
{
  for (vp = &values[0]; vp < &values[VA];)
  {
    *vp++ = 0;
  }
}

代码2:

#define VA 5
float values[VA];
float* vp;
int main()
{
  for (vp = &values[VA]; vp > &values[0];)
  {
    *--vp = 0;
  }
}

代码1中,是从低地址向高地址,是用低地址与高地址比较

代码2中,是从高地址向低地址,是用高地址与低地址比较

如图:

注意:

在代码2中,有人想进行简化,如下:

for (vp = &values[VA-1]; vp >= &values[0]; vp--)
{
  *vp = 0;
}

但这么简化并不好,原因如下

标准规定:允许指向数组元素的指针与指向数组最后一个元素的那个内存位置的指针进行比较,但,不允许与只想第一个元素之前的那个内存位置的指针进行比较。

当运行到vp==-1时,在条件判断部分,他便是第一个元素之前的那个内存位置的指针,所以在某些情况下,这是不被允许的

(了解即可)

(在C++中,创建数组,会在数组首元素的前一个地址开辟一个空间,用于系统维护这个数组,但实际上数组返回的是其首元素)

5.指针和数组

概念辨析:

指针就是指针,指针变量就是一个变量,存放的地址,指针变量的大小是4/8

数组就是数组,可以存放一组数,数组的大小是取决于元素的类型和个数

二者关系:

数组的数组名是数组首元素的地址,其地址是可以存储指针变量中。

通过指针可以访问这个数组的元素。

注意:

&数组名:

表示的是数组的地址,虽然在数值上,数组的地址和数组首元素的地址相同,但二者的意义和类型都不同

区别是:在与整数进行运算时,其跳过的字节数不同

6.二级指针

存放一级指针变量的地址的变量,定义为二级指针变量

比如:

int ** pp = &p

其解引用时,所需的操作符也是两个

提示:

对于二级指针pp类型的补充说明:

后面的那个星号(此处打不出来那个符号)是在说明pp是指针变量

而int*是在说明pp所指向的变量类型是整型指针

7.指针数组

定义:存放指针的数组

概念辨析拓展:

此处可以看我另一篇文章中的第二题中的概念辨析

点击此处跳转

结语

对于指针的初步介绍就到这里了,我们下次再见。



相关文章
|
21天前
|
存储 NoSQL 编译器
【C语言】指针的神秘探险:从入门到精通的奇幻之旅 !
指针是一个变量,它存储另一个变量的内存地址。换句话说,指针“指向”存储在内存中的某个数据。
74 3
【C语言】指针的神秘探险:从入门到精通的奇幻之旅 !
|
21天前
|
存储 编译器 C语言
【C语言】指针大小知多少 ?一场探寻C语言深处的冒险 !
在C语言中,指针的大小(即指针变量占用的内存大小)是由计算机的体系结构(例如32位还是64位)和编译器决定的。
46 9
|
21天前
|
安全 程序员 C语言
【C语言】指针的爱恨纠葛:常量指针vs指向常量的指针
在C语言中,“常量指针”和“指向常量的指针”是两个重要的指针概念。它们在控制指针的行为和数据的可修改性方面发挥着关键作用。理解这两个概念有助于编写更安全、有效的代码。本文将深入探讨这两个概念,包括定义、语法、实际应用、复杂示例、最佳实践以及常见问题。
40 7
|
1月前
|
存储 C语言
C语言如何使用结构体和指针来操作动态分配的内存
在C语言中,通过定义结构体并使用指向该结构体的指针,可以对动态分配的内存进行操作。首先利用 `malloc` 或 `calloc` 分配内存,然后通过指针访问和修改结构体成员,最后用 `free` 释放内存,实现资源的有效管理。
105 13
|
25天前
|
存储 程序员 编译器
C 语言数组与指针的深度剖析与应用
在C语言中,数组与指针是核心概念,二者既独立又紧密相连。数组是在连续内存中存储相同类型数据的结构,而指针则存储内存地址,二者结合可在数据处理、函数传参等方面发挥巨大作用。掌握它们的特性和关系,对于优化程序性能、灵活处理数据结构至关重要。
|
25天前
|
算法 C语言
C语言中的文件操作技巧,涵盖文件的打开与关闭、读取与写入、文件指针移动及注意事项
本文深入讲解了C语言中的文件操作技巧,涵盖文件的打开与关闭、读取与写入、文件指针移动及注意事项,通过实例演示了文件操作的基本流程,帮助读者掌握这一重要技能,提升程序开发能力。
83 3
|
25天前
|
存储 算法 程序员
C 语言指针详解 —— 内存操控的魔法棒
《C 语言指针详解》深入浅出地讲解了指针的概念、使用方法及其在内存操作中的重要作用,被誉为程序员手中的“内存操控魔法棒”。本书适合C语言初学者及希望深化理解指针机制的开发者阅读。
|
25天前
|
程序员 C语言
C语言中的指针既强大又具挑战性,它像一把钥匙,开启程序世界的隐秘之门
C语言中的指针既强大又具挑战性,它像一把钥匙,开启程序世界的隐秘之门。本文深入探讨了指针的基本概念、声明方式、动态内存分配、函数参数传递、指针运算及与数组和函数的关系,强调了正确使用指针的重要性,并鼓励读者通过实践掌握这一关键技能。
36 1
|
29天前
|
存储 C语言 计算机视觉
在C语言中指针数组和数组指针在动态内存分配中的应用
在C语言中,指针数组和数组指针均可用于动态内存分配。指针数组是数组的每个元素都是指针,可用于指向多个动态分配的内存块;数组指针则指向一个数组,可动态分配和管理大型数据结构。两者结合使用,灵活高效地管理内存。
|
29天前
|
存储 NoSQL 编译器
C 语言中指针数组与数组指针的辨析与应用
在C语言中,指针数组和数组指针是两个容易混淆但用途不同的概念。指针数组是一个数组,其元素是指针类型;而数组指针是指向数组的指针。两者在声明、使用及内存布局上各有特点,正确理解它们有助于更高效地编程。