自学内容网 自学内容网

C语言指针简介篇

1. 指针的基本概念

  • 什么是指针: 指针是一个变量,用于存储另一个变量的内存地址。通过指针,程序可以直接访问和操作存储在内存中的数据。

  • 指针与变量的关系: 在C语言中,每个变量都有一个地址,可以使用&运算符获取变量的地址。例如,&x表示变量x的地址。指针在内存也有自己的地址,二级指针可以简单理解为指向指针的指针

2. 指针的定义与初始化

  • 指针的定义: 定义一个指针时,需要指定它所指向的数据类型。例如:

    int *ptr; // ptr是一个指向整数的指针

    指针的初始化: 指针在使用之前需要被初始化。可以通过将指针指向一个变量的地址来初始化:

  • int x = 10; int *ptr = &x; // ptr现在指向x的地址 

3. 指针的使用

  • 访问指针所指向的值: 使用解引用运算符*可以访问指针所指向的内存地址的值

    int value = *ptr; // value现在是x的值,即10
  • 修改指针所指向的值: 通过指针可以直接修改指针所指向的变量的值:

    *ptr = 20; // x的值现在变为20

4. 指针的运算

  • 指针加减法: 指针可以进行加减运算,这对于数组和动态内存分配非常有用。例如,指针加1将指向下一个同类型元素的地址:

    int arr[] = {1, 2, 3}; int *ptr = arr; // 指向数组的第一个元素 ptr++; // 现在ptr指向arr[1]
  • 指针与数组: 数组名实际上是指向数组第一个元素的指针。因此,可以使用指针遍历数组:

    for (int i = 0; i < 3; i++) { printf("%d ", *(arr + i)); // 使用指针访问数组元素 }

5. 指针的类型

  • 指向不同类型的指针: C语言支持不同类型的指针,如int*, float*, char*等。每种类型的指针在进行算术运算时,增加的值是根据指向的类型的大小来计算的。

  • 空指针: 空指针是一个不指向任何有效内存的指针,通常用NULL表示。可以使用空指针来检查指针是否已经被初始化:

    int *ptr = NULL; // ptr是一个空指针

6. 动态内存分配

  • 动态内存分配函数: C语言提供了malloc(), calloc(), realloc()free()等函数进行动态内存分配和管理。例如:

    int *arr = (int*)malloc(5 * sizeof(int)); // 分配5个整数的内存
  • 释放内存: 使用free()函数释放之前分配的内存,以避免内存泄漏:

    free(arr); // 释放动态分配的内存

7. 指针的常见问题

  • 未初始化的指针: 使用未初始化的指针(野指针)会导致未定义行为。始终在使用指针之前进行初始化。

  • 指针越界: 访问指针指向的内存范围之外的数据会导致未定义行为。确保在访问指针指向的内存时遵循边界检查。

  • 多次释放: 对同一块内存多次调用free()会导致程序崩溃。使用后,最好将指针设为NULL以避免这种情况。

  • 内存泄漏: 动态分配的内存在不再使用时应及时释放。检查每个malloc()calloc()调用,确保有对应的free()调用。

8.二级指针、指针数组、数组指针

二级指针(Pointer to Pointer)
  • 定义: 二级指针是一个指向另一个指针的指针。其类型为 type**,其中 type 是指向的基本数据类型。

  • 定义和初始化

    int x = 10; int *ptr = &x; // ptr是一个指向int的指针 int **pptr = &ptr; // pptr是一个指向指针ptr的指针

  • 使用

    • 访问二级指针所指向的值:
      printf("%d\n", **pptr); // 输出10,**pptr首先解引用到ptr,然后解引用到x

    • 修改值:
      **pptr = 20; // 通过pptr修改x的值为20 printf("%d\n", x); // 输出20
  • 应用场景: 二级指针常用于动态分配二维数组、传递多级指针到函数等场景。

2. 指针数组(Array of Pointers)
  • 定义: 指针数组是一个数组,其中的每个元素都是指向同一类型数据的指针。

  • 定义和初始化

    int *ptrs[3]; // 声明一个包含3个int指针的数组
    int a = 1, b = 2, c = 3; 
    ptrs[0] = &a; 
    // 将ptrs[0]指向a ptrs[1] = &b; 
    // 将ptrs[1]指向b ptrs[2] = &c;
    // 将ptrs[2]指向c

  • 使用

    • 访问指针数组中的值:
      for (int i = 0; i < 3; i++) { printf("%d\n", *ptrs[i]); // 输出1, 2, 3 }
  • 应用场景: 指针数组在需要处理多个指针的情况,如存储字符串数组(字符指针数组)时非常有用。

3. 数组指针(Pointer to an Array)
  • 定义: 数组指针是一个指针,用于指向整个数组,而不是数组的单个元素。其类型为 type (*)[size],其中 type 是数组元素的类型,size 是数组的大小。

  • 定义和初始化

    int arr[3] = {1, 2, 3}; int (*p)[3] = &arr; // p是一个指向包含3个int的数组的指针
  • 使用

    • 通过数组指针访问数组元素:
      //(*p)=arr
      printf("%d\n", (*p)[0]); //*(p+0)等价(*p)[0]
      // 输出1
      printf("%d\n", (*p)[1]); //*(p+1)等价(*p)[1]
      // 输出2 
      printf("%d\n", (*p)[2]); //*(p+2)等价(*p)[2]
      // 输出3
  • 应用场景: 数组指针常用于函数参数,传递一个完整的数组,而不是数组的首地址。这可以在函数中保证数组大小。

总结
  • 二级指针:指向指针的指针,常用于动态分配多维数组。
  • 指针数组:存储指针的数组,每个元素都是一个指针,适合处理多个指针。
  • 数组指针:指向数组的指针,便于在函数中传递整个数组。

 


原文地址:https://blog.csdn.net/2301_80950699/article/details/142500342

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!