• 深入理解指针(c语言)


    一、使用指针访问数组

    可以使用指针来访问数组元素。例如,可以声明一个指针变量并将其指向数组的第一个元素,然后通过递增指针的方式来访问数组的其他元素:

    #include
    int main()
    {
        int arr[5] = { 1, 2, 3, 4, 5 };
        int* ptr = arr; // 指针指向数组的第一个元素
    
        for (int i = 0; i < 5; i++)
        {
            printf("%d ", *ptr); // 访问数组元素
            ptr++; // 指针递增,指向下一个元素
        }
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 输出结果:
      在这里插入图片描述

    二、数组名的理解

    在C语言中,数组名有时代表数组中首元素的地址,有时代表整个数组,视情况而定。

    1、数组首元素的地址

    例1: 定义一个整型数组arr,可以用数组名arr表示数组的首地址,作为参数传递给函数:

    #include
    
    void printArray(int arr[], int size) 
    {
        for (int i = 0; i < size; i++) 
        {
            printf("%d ", arr[i]);
        }
        printf("\n");
    }
    
    int main() 
    {
        int arr[5] = {1, 2, 3, 4, 5};
        printArray(arr, 5);
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 输出结果:
      在这里插入图片描述

    这里,printArray函数的参数形式为int arr[],实际上是将数组名arr作为指针常量传递给函数。


    例2: 用数组名访问数组中的元素:

    #include
    int main()
    {
    	int arr[5] = { 1, 2, 3, 4, 5 };
    	int* ptr = arr;
    	printf("%d\n", *ptr);    // 输出1
    	ptr++;
    	printf("%d\n", *ptr);    // 输出2
    	return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 输出结果:
      在这里插入图片描述

    这里,arr和ptr都指向数组的第一个元素,可以通过指针操作来访问数组的元素。


    2、整个数组

    例1: sizeof中单独放数组名,这⾥的数组名表⽰整个数组,计算的是整个数组的⼤⼩(单位是字节):

    #include
    int main()
    {
    	int arr[5] = { 1, 2, 3, 4, 5 };
    	int size = sizeof(arr);
    	printf("%d\n", size);
    	return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 输出结果:
      在这里插入图片描述
      例2: &数组名,这⾥的数组名表⽰整个数组,取出的是整个数组的地址(整个数组的地址和数组⾸元素的地址是有区别的)
    #include
    int main()
    {
    	int arr[5] = { 1,2,3,4,5 };
    	printf("&arr[0]   = %p\n", &arr[0]);
    	printf("&arr[0]+1 = %p\n", &arr[0] + 1);
    	printf("arr       = %p\n", arr);
    	printf("arr+1     = %p\n", arr + 1);
    	printf("&arr      = %p\n", &arr);
    	printf("&arr+1    = %p\n", &arr + 1);
    	return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 输出结果:
      在这里插入图片描述
      这⾥我们发现&arr[0]和&arr[0]+1相差4个字节,arr和arr+1相差4个字节,是因为&arr[0]和arr都是⾸元素的地址,+1就是跳过⼀个元素。
      但是&arr和&arr+1相差20个字节,这就是因为&arr是数组的地址,+1操作是跳过整个数组的。

    除了这两个例子之外,其他任何地⽅使⽤数组名都表⽰⾸元素的地址。

    三、一维数组传参的本质

    在C语言中,一维数组传参时,实际上传递的是数组的首地址,也就是数组名。函数可以通过修改传入的数组来修改实际的数据。

    #include
    
    void modifyArray(int arr[], int size) 
    {
        for (int i = 0; i < size; i++) 
        {
            arr[i] *= 2; // 修改数组元素
        }
    }
    
    int main() 
    {
        int arr[5] = {1, 2, 3, 4, 5};
        modifyArray(arr, 5); // 传递数组名作为参数
        for (int i = 0; i < 5; i++) 
        {
            printf("%d ", arr[i]); // 输出修改后的数组
        }
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 输出结果:
      在这里插入图片描述

    四、冒泡排序

    冒泡排序是一种基本的排序算法,通过多次比较和交换来实现。算法的核心思想是从数组的第一个元素开始,依次比较相邻的两个元素如果前一个元素大于后一个元素,则交换它们的位置

    #include
    
    void bubbleSort(int arr[], int size) 
    {
        for (int i = 0; i < size - 1; i++) 
        {
            for (int j = 0; j < size - i - 1; j++) 
            {
                if (arr[j] > arr[j + 1]) 
                {
                    int temp = arr[j];
                    arr[j] = arr[j + 1];
                    arr[j + 1] = temp;
                }
            }
        }
    }
    
    int main() 
    {
        int arr[5] = {5, 4, 3, 2, 1};
        bubbleSort(arr, 5);
        for (int i = 0; i < 5; i++) 
        {
            printf("%d ", arr[i]);
        }
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 输出结果:
      在这里插入图片描述

    五、二级指针

    二级指针是指向指针的指针。通过使用二级指针,可以在函数中修改指针的值,间接修改指针指向的变量。

    #include
    
    void changeValue(int **ptr) 
    {
        int newValue = 10;
        *ptr = &newValue; // 修改二级指针指向的变量
    }
    
    int main() 
    {
        int value = 5;
        int *ptr = &value;
        changeValue(&ptr); // 传递二级指针作为参数
        printf("%d", *ptr); // 输出修改后的值
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 输出结果:
      在这里插入图片描述

    六、指针数组

    指针数组是一个数组,其中的每个元素都是指针。通过指针数组,可以存储多个指针,并进行相应的操作。

    #include
    
    int main() 
    {
        int a = 1, b = 2, c = 3;
        int *ptrArray[3]; // 声明指针数组
    
        ptrArray[0] = &a; // 将指针赋值给数组元素
        ptrArray[1] = &b;
        ptrArray[2] = &c;
    
        for (int i = 0; i < 3; i++) 
        {
            printf("%d ", *ptrArray[i]); // 输出数组元素指向的值
        }
    
        return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 输出结果:
      在这里插入图片描述
  • 相关阅读:
    2D物理系统——物理材质 & 恒定力
    开源一个RAG大模型本地知识库问答机器人-ChatWiki
    华为云云耀云服务器L实例评测 | 基于docker部署nacos2.2.3服务
    RPA技术介绍与应用价值
    JMeter—逻辑控制器
    生活笔记——嵌入式人工智能小记(2022_8_7)
    在数组第一行插入带键值的元素,内置函数 array_unshift 不好使,第一次循环中插入即可。
    Arduino与Proteus仿真实例-密码门禁控制仿真
    【Python】sort 排序
    《下一代互联网(IPv6)搭建与运维》1+X证书
  • 原文地址:https://blog.csdn.net/2301_81988400/article/details/136221999