• 10 数组和指针


    1 数组

    在这里插入图片描述

    /* some array declarations */
    int main(void){
     	float candy[365]; /* array of 365 floats */
     	char code[12]; /* array of 12 chars */
     	int states[50]; /* array of 50 ints */
     	...
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    在这里插入图片描述

    1.1 初始化数组

    在这里插入图片描述
    C语言通过如下的方式初始化数组:

    int main(void){
     	int powers[8] = {1,2,4,6,8,16,32,64}; /* ANSI C and later */
     	...
    } 
    
    • 1
    • 2
    • 3
    • 4

    在这里插入图片描述

    注意:使用const声明数组
    有时需要把数组设置为只读。这样,程序只能从数组重检索值,不能把新值写入数组。要创建只读数组,应该用const声明和初始化数组。例如如下的形式:
    const int days[12] = {31,28,31,30,31,30,31,31,30,31,30,31};

    如果未初始化数组,那么可能输出随机值,程序10.2演示了这种情况:

    /* no_data.c -- uninitialized array */
    #include <stdio.h>
    #define SIZE 4
    
    int main(void){
     	int no_data[SIZE]; /* uninitialized array */
     	int i;
     	printf("%2s%14s\n", "i", "no_data[i]");
     	for (i = 0; i < SIZE; i++)
     		printf("%2d%14d\n", i, no_data[i]);
     	return 0;
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    程序的一个可能输出如下:

    i 	no_data[i]
    0 	0
    1 	4204937
    2 	4219854
    3 	2147348480 
    
    • 1
    • 2
    • 3
    • 4
    • 5

    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    程序10.3 somedata.c

    /* some_data.c -- partially initialized array */
    #include <stdio.h>
    #define SIZE 4
    
    int main(void){
     	int some_data[SIZE] = {1492, 1066};
     	int i;
     	printf("%2s%14s\n", "i", "some_data[i]");
     	for (i = 0; i < SIZE; i++)
     		printf("%2d%14d\n", i, some_data[i]);
     	return 0;
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    程序的输出如下:

    i 	some_data[i]
    0 	1492
    1 	1066
    2 	0
    3 	0
    
    • 1
    • 2
    • 3
    • 4
    • 5

    在这里插入图片描述
    程序 10.4 day_mon2.c

    /* day_mon2.c -- letting the compiler count elements */
    #include <stdio.h>
    
    int main(void){
     	const int days[] = {31,28,31,30,31,30,31,31,30,31};
     	int index;
     	for (index = 0; index < sizeof days / sizeof days[0]; index++)
     		printf("Month %2d has %d days.\n", index +1, days[index]);
     	return 0;
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    在这里插入图片描述
    程序输出如下:

    Month 1 has 31 days.
    Month 2 has 28 days.
    Month 3 has 31 days.
    Month 4 has 30 days.
    Month 5 has 31 days.
    Month 6 has 30 days.
    Month 7 has 31 days.
    Month 8 has 31 days.
    Month 9 has 30 days.
    Month 10 has 31 days. 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    在这里插入图片描述

    1.2 指定初始化器(C99)

    待补充 301

    1.3 给数组元素赋值

    待补充 302

    1.4 数组边界

    待补充 303

    1.5 指定数组的大小

    待补充 304

    2 多维数组

    待补充 305

    3 指针和数组

    数组名是数组首元素的地址。也就是说,如果flizny是一个数组,下面的语句成立:

    flizny == &flizny[0]; // name of array is the address of the first element 
    
    • 1

    在这里插入图片描述
    程序 10.8 pnt_add.c

    // pnt_add.c -- pointer addition
    #include <stdio.h>
    #define SIZE 4
    
    int main(void){
     	short dates [SIZE];
     	short * pti;
     	short index;
     	double bills[SIZE];
     	double * ptf;
     	pti = dates; // assign address of array to pointer
     	ptf = bills;
     	printf("%23s %15s\n", "short", "double");
     	for (index = 0; index < SIZE; index ++)
     		printf("pointers + %d: %10p %10p\n", index, pti + index, ptf + index);
     	return 0;
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    下面是该例的输出示例:

    				short 			double
    pointers + 0: 	0x7fff5fbff8dc 	0x7fff5fbff8a0
    pointers + 1: 	0x7fff5fbff8de 	0x7fff5fbff8a8
    pointers + 2: 	0x7fff5fbff8e0 	0x7fff5fbff8b0
    pointers + 3: 	0x7fff5fbff8e2 	0x7fff5fbff8b8 
    
    • 1
    • 2
    • 3
    • 4
    • 5

    在系统中,地址按字节编址,short类型占2字节,double类型占8字节。在C重,指针加1指的是增加一个存储单元。对数组而言,这意味着加一后端地址是下一个元素的地址,而不是下一个字节的地址。这是为什么必须声明指针所指向对象类型的原因之一。只知道地址不够,因为计算机要知道储存对象需要多少字节。

    4 函数、数组和指针

    假设要编写一个处理数组的函数,该函数返回数组重所有元素之和,待处理的是名为marbles的int类型数组。此时我们可以进行如下的调用:

    total = sum(marbles); 
    
    • 1

    此时函数原型如下(由于数组名是数组首元素的地址,所以实际参数marlbes是要给储存int类型值的地址,应把它赋给一个指针形式参数):

     int sum(int * ar); // corresponding prototype 
    
    • 1

    在这里插入图片描述
    在这里插入图片描述

    int sum(int * ar){ // corresponding definition
     	int i;
     	int total = 0;
     	for( i = 0; i < 10; i++) // assume 10 elements
     		total += ar[i]; // ar[i] the same as *(ar + i)
     	return total;
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    在这里插入图片描述

    int sum(int * ar, int n){ // more general approach
     	int i;
     	int total = 0;
     	for( i = 0; i < n; i++) // use n elements
     		total += ar[i]; // ar[i] the same as *(ar + i)
     	return total;
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

    4.1 使用指针形参

    在这里插入图片描述
    程序 10.11 sum_arr2.c

    /* sum_arr2.c -- sums the elements of an array */
    #include <stdio.h>
    #define SIZE 10
    
    int sump(int * start, int * end);
    
    int main(void){
     	int marbles[SIZE] = {20,10,5,39,4,16,19,26,31,20};
     	long answer;
     	answer = sump(marbles, marbles + SIZE);
     printf("The total number of marbles is %ld.\n", answer);
     return 0;
     }
     
    /* use pointer arithmetic */
    int sump(int * start, int * end){
     	int total = 0;
     	while (start < end){
     		total += *start; // add value to total
     		start++; // advance pointer to next element
     	}
     	return total;
    } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23

    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

    5 指针操作

  • 相关阅读:
    字节一面:go的协程相比线程,轻量在哪?
    【操作系统】内存管理(二)—— 程序运行的基本过程和要求
    Semtech 12亿美元重大并购,物联网领域有机会出现下一个“LoRa 生态”吗?
    优雅处理Golang中的异常
    路由器安全性怎么提高
    化繁为简 面板式空调网关亮相上海智能家居展 智哪儿专访青岛中弘赵哲海
    数组:4.覆盖的点数
    【CCF CSP-20161203】权限查询
    vue 检查指定路由是否存在
    Vue-Router4 学习记录
  • 原文地址:https://blog.csdn.net/kking_edc/article/details/125363975