过关斩将,擒“指针”(下)(1)

简介: 过关斩将,擒“指针”(下)

1.字符指针

字符指针:指向字符的指针,指针类型为 char*


char ch = 'a';
  char* pc = &ch;

一般使用方法:


#include<stdio.h>
int main()
{
  char ch = 'a';
  char* pc = &ch;
  *pc = 'b';
  printf("%c\n", ch);
  return 0;
}

还有一种使用方法:


#include<stdio.h>
int main()
{
  const char* pc = "abcdef";
  printf("%s\n", pc);
  return 0;
}

思考1:为什么 const char* pc = "abcdef" 前面要加 const?


答:因为字符指针 pc 指向的是常量字符串,常量是不能发生改变的,所以加 const 避免修改常量字符串。


思考2:const char* pc = "abcdef",是把 abcdef 字符串放入字符指针变量 pc 中吗?


答:不是,是把字符串中首字符的地址放入了 pc 中,也就是把 a 的地址放在 pc 中 。


q1.png


面试题:


#include<stdio.h>
int main()
{
  char arr[] = { "abcdef" };
  char brr[] = { "abcdef" };
  const char* crr = "abcdef";
  const char* drr = "abcdef";
  if (arr == brr)
  {
  printf("arr and brr are same\n");
  }
  else
  {
  printf("arr and brr not are same\n");
  }
  if (crr == drr)
  {
  printf("crr and drr are same\n");
  }
  else
  {
  printf("crr and drr not are same\n");
  }
  return 0;
}


运行结果:


q2.png


arr 和 brr 是字符数组,是把 abcdef 存储在字符数组中,它们的内存不是同一块,所以它们的地址也就不相同。而 crr 和 drr 是字符指针,是把 abcdef 常量字符串的首元素地址存储字符指针中,所以它们指向的是同一块内存空间。

q3.png

2.指针数组

指针数组:它是一个数组,数组中的每个元素都是类型指针


int* arr[10]; //整形指针的数组

首先 arr 先跟 [10] 结合说明它是一个有十个元素数组,每个元素都是 int* 类型的指针。


3.数组指针

3.1数组指针的定义

数组指针:是一个指针,指向的是一个数组


int arr[6] = { 1, 2, 3, 4, 5, 6 };
  int(*pi)[6] = &arr;

pi 先和 * 结合说明它是一个指针变量,[6] 说明它指向了一个数组,数组中有 6 个元素,int 说明每个元素都是 int 类型。


注:[] 的优先级要高于 * 号的,所以必须加上()来保证 p 先和 * 结合。

3.2 &数组名 vs 数组名

int arr[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };

数组名 arr :表示首元素的地址

&数组名:表示整个数组的地址

q1.png


arr 和 &arr 它们打印出来的地址虽然一样 ,但它们代表的含义不一样。arr 表示数组首元素的地址,而 &arr 表示整个数组的地址,arr + 1跳过了一个元素,而&arr + 1跳过了整个数组。


q2.png


sizeof(arr[0])是计算 arr[0] 所占空间大小,而 sizeof(arr)是计算整个数组所占空间大小 。


结论:&数组名 和 sizeof(数组名) 表示整个数组,其余的数组名都表示数组首元素的地址。


3.3数组指针的使用

既然数组指针指向的是数组,那数组指针中存放的也就是数组的地址。


#include<stdio.h>
int main()
{
  int arr[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 };
  int(*pi)[10] = &arr;
  return 0;
}

把数组 arr 的地址赋值给数组指针变量 p ,但我们一般很少这样写代码 ,因为这样写代码没有任何的意义。


一般我们将数组指针用于二维数组


#include<stdio.h>
void print_arr(int(*arr)[3], int row, int col)
{
  for (int i = 0; i < row; i++)
  {
  for (int j = 0; j < col; j++)
  {
    printf("%d ", arr[i][j]);
  }
  printf("\n");
  }
}
int main()
{
  int arr[3][3] = { { 1, 2, 3 }, { 4, 5, 6 }, { 7, 8, 9 } };
  print_arr(arr, 3, 3);
  return 0;
}

数组名arr,表示首元素的地址  。但是二维数组的首元素是二维数组的第一行  ,所以这里传递的arr,其实相当于第一行的地址,是一维数组的地址。


学了指针数组和数组指针我们来一起回顾并看看下面代码的意思:


int arr[5];//整型数组
int *parr1[10];//数组指针
int (*parr2)[10];//指针数组
int (*parr3[10])[5];//???
 int (*parr3[10])[5]:

首先 parr3 跟 [10] 结合说明它是一个数组,每个元素都是指针数组类型。


相关文章
|
存储
过关斩将,擒“指针”(上)(1)
过关斩将,擒“指针”(上)
107 0
过关斩将,擒“指针”(上)(1)
|
编译器
过关斩将,擒“指针”(上)(2)
过关斩将,擒“指针”(上)
110 0
过关斩将,擒“指针”(上)(2)
|
6月前
|
C语言
指针进阶(C语言终)
指针进阶(C语言终)
|
2月前
|
C语言
无头链表二级指针方式实现(C语言描述)
本文介绍了如何在C语言中使用二级指针实现无头链表,并提供了创建节点、插入、删除、查找、销毁链表等操作的函数实现,以及一个示例程序来演示这些操作。
28 0
|
3月前
|
存储 人工智能 C语言
C语言程序设计核心详解 第八章 指针超详细讲解_指针变量_二维数组指针_指向字符串指针
本文详细讲解了C语言中的指针,包括指针变量的定义与引用、指向数组及字符串的指针变量等。首先介绍了指针变量的基本概念和定义格式,随后通过多个示例展示了如何使用指针变量来操作普通变量、数组和字符串。文章还深入探讨了指向函数的指针变量以及指针数组的概念,并解释了空指针的意义和使用场景。通过丰富的代码示例和图形化展示,帮助读者更好地理解和掌握C语言中的指针知识。
|
4月前
|
C语言
【C初阶——指针5】鹏哥C语言系列文章,基本语法知识全面讲解——指针(5)
【C初阶——指针5】鹏哥C语言系列文章,基本语法知识全面讲解——指针(5)
|
4月前
|
C语言
【C初阶——指针4】鹏哥C语言系列文章,基本语法知识全面讲解——指针(4)
【C初阶——指针4】鹏哥C语言系列文章,基本语法知识全面讲解——指针(4)
|
4月前
|
存储 编译器 C语言
【C初阶——指针3】鹏哥C语言系列文章,基本语法知识全面讲解——指针(3)
【C初阶——指针3】鹏哥C语言系列文章,基本语法知识全面讲解——指针(3)
|
5月前
|
编译器 C语言
【C语言初阶】指针篇—下
【C语言初阶】指针篇—下