精华内容
下载资源
问答
  • 例如数组指针的本质就是一个指针,一个指向数组的指针;而指针数组的本质就是一个数组,一个成员都是指针的数组。 1.数组指针 1.1 基本概念 数组指针,即指向一个数组的指针。可以指向一维数组,也可以指向二维数组...


    数组指针和指针数组,从字面上区分的方法就是:本质看最后两个字。例如数组指针的本质就是一个指针,一个指向数组的指针;而指针数组的本质就是一个数组,一个成员都是指针的数组。

    1.数组指针

    1.1 基本概念

    数组指针,即指向一个数组的指针。可以指向一维数组,也可以指向二维数组(三维及以上数组一般不用)。

    1.2 定义格式

    int (*p)[n]=NULL;
    
    p = 数组名;   //当数组是一维数组时,直接写数组名编译器会警告,但是运行正常。写成“&数组名”不会警告。对于二维及以上数组,直接写数组名不会警告。
    

    解析:

    类型说明符 (*指针变量名)[长度]。

    其中“类型说明符”为所指数组的数据类型。* 表示其后的变量p是指针类型,它指向的对象是一个整体,即一维数组(不能拆开此数组)。

    【注1】

    首先 运算符[ ] 的优先级比 * 高,虽然在优先级表中 [ ] 的优先级最高,其次是 ( ) 。但是 ( ) 有强制结合的功能,所以这里p是和*结合的,而不是[]。

    【注2】

    当数值指针指向一维数组时,n是一维数组元素的个数。
    当数值指针指向二维数组时,n是二维数组的列数,即按行拆分成一维数组后,一维数组的个数。

    【注3】

    数组指针也叫“行指针”,原因是数组指针指向的数组不管是一维数组,还是二维数组,指针变量p指向的都是行。

    【例】用“数组指针”分别指向并遍历一维数组和二维数组的所有元素。

    #include <stdio.h>
    
    int main(void){
    	int i,j;
    	
    	int a[5]={1,2,3,4,5};
    	int b[3][4]={1,2,3,4,5,6,7,8,9,10,11,12};
    	
    	int (*p1)[5]=NULL;
    	int (*p2)[4]=NULL;
    	
    	p1=a; //会警告提示指针类型不匹配,但是可以运行正常,应该是C隐式进行类型转换。写成 p1=&a;无警告无错误 
    	p2=b;
    	
    	printf("遍历输出一维数组元素\n");
    	//通过数组指针来遍历输出一维数组a的元素 
    	for(i=0;i<5;i++){
    		printf("%2d", *((*p1+0)+i) );
    	}
    	
    	printf("\n");
    	
    	printf("遍历输出二维数组元素\n");
    	for(i=0;i<3;i++){
    		for(j=0;j<4;j++){
    			printf("%3d", *(*(p2+i)+j) );
    		}
    		printf("\n");
    	}
    	
    	return 0;
    }
    

    运行结果:
    在这里插入图片描述

    1.3 扩展:指向二维数组的数组指针如何遍历二维数组元素?

    在上例中,数组指针p2指向二维数组b。

    下面探索一下如何使用数组指针 p2 来访问二维数组b中的每个元素。

    1. 数组指针p2指向二维数组 b 的开头,也即第 0 行;p2+1前进一行,指向第 1 行。

    2. *(p2+1)表示取地址上的数据,也就是整个第 1 行数据。注意是一行数据,是多个数据,不是第1 行中的第0个元素。

    3. *(p2+1)+1表示第 1 行第 1 个元素的地址。怎么理解?

      *(p2+1)单独使用时表示的是第1行整体数据,放在表达式中会被转换为第 1 行数据的首地址,也就是第 1 行第 0 个元素的地址,因为使用整行数据没有实际的含义,编译器遇到这种情况都会转换为指向该行第 0 个元素的指针;就像一维数组的名字,在定义时或者和 sizeof、& 一起使用时才表示整个数组,出现在表达式中就会被转换为指向数组第 0 个元素的指针。

    4. *(*(p2+1)+1)表示第 1 行第 1 个元素的值。很明显,增加一个 * 表示取地址上的数据。

    2.指针数组

    2.1 基本概念

    具有指针类型元素的数组称为指针数组,实质上就是一个数组。

    2.2 定义格式

    类型说明符 *指针变量名[长度];

    【注】

    如:int *p[n]; //int *(p[n])也是一个指针数组,这里小括号可有可无。
    []优先级比 * 高,所以先与p结合成为一个数组,然后int *说明该数组中每个元素的数据类型都是“整形指针类型”。

    展开全文
  • 之前对数组的概念一直没有理解透彻,只觉得数组名就是个常量指针而已,用法基本的指针差不多。所以当我尝试用二级指针去访问二维数组时,就经常会出错。下面就是刚开始写的个错误的程序: #include &...

    之前对数组的概念一直没有理解透彻,只觉得数组名就是个常量指针而已,用法和基本的指针差不多。所以当我尝试用二级指针去访问二维数组时,就经常会出错。下面就是刚开始写的一个错误的程序:

    #include <stdio.h>
    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int **pArray = NULL;
    
    pArray = iArray;
    
    printf("array[0][0] = %d\n", pArray[0][0]);
    printf("array[1][2] = %d\n", pArray[1][2]);
    
    return 0;
    }

     


    开始的时候我是这样分析的:本来数组和指针就差不多,一维数组和一维指针对应,那么二维数组名应该和二维指针差不多,所以上面那个程序是没有错的,应该打 印出的是1和6。但是当我实际编译运行的时候,却出现了段错误,也就是我访问了不该访问的地址空间。那错误到底出在什么地方呢?正确的程序应该怎么写呢?
    为了解决问题,不得不让我重新理解数组的含义。仔细翻阅一些书籍后,我发现其实数组并不是我原来想象的那么简单:一个常量指针标识的一群变量的集合。数组 应该也算是一个完备的变量类型:有名字,有大小,也有地址。只不多就是名字和它的地址一样罢了。也正是因为数组有大小,所以当用sizeof对数组名进行 运算时,算出来的是实际数组的大小,而不是指针的大小。
    也正是因为这样,所以指向数组的指针和指向指针的指针也大不一样。它们俩最明显的不同就是表现在指针步进的时候。我们知道指针在进行++运算的时候,跨越 的实际地址取决于指针指向的数据类型:对于一般的32位机来说,假如指向的是int型数据,跨越的实际地址就是4,指向的是指针型数据,跨越的实际地址也 是4,当指向的是数组类型的时候,跨越的实际地址就是数组的长度了。
    现在再回头分析上面那个错误程序,根据下标引用符号[]的运算规则,我们知道pArray[0][0]其实就是**pArray,而iArray实际上只 是个数组变量名,而它的值就是整个数组的开始地址(其实&iArray,iArray,iArray[0]以及&iArray的值都是数 组的开始地址,都是在编译过程中编译器赋予的值)。那么其实*pArray就已经是iArray[0][0]的值了,也就是1,而**pArray则是去 访问地址为1的地址空间中的数据,自然会出段错误。
    其实用指针访问二维数组可以直接用一级指针就可以了。比如下面这个程序:

     
    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int *pArray = NULL;pArray = iArray;
    printf("array[0][0] = %d\n", *pArray);
    printf("array[1][2] = %d\n", *(pArray + 1 * 3 + 2));
    
    return 0;
    }

     


        因为数组本身在地址空间中就是连续排列的,根据行数和列数,我们自己计算出访问单元的地址偏移量就可以用一级指针轻松遍历二维数组中的所有数据了。
    我们还可以尝试用指向数组的指针来访问二维数组的成员。下面就是事例程序:
    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int (*pArray)[3] = NULL;pArray = iArray;
    printf("array[0][0] = %d\n", pArray[0][0]);
    printf("array[1][2] = %d\n", pArray[1][2]);
    
    return 0;
    }

     

    简单分析一下这个程序:我们知道[]运算符的结合方向是由左向右,pArray[1][2]就等价于(* (pArray + 1))[2],而由于pArray是数组指针,而且数组的长度为3,所以* (pArray + 1)就表示iArray[1]这个数组,则pArray[1][2]则就完全等价于iArray[1][2]。

    如果非得想用二级指针来访问二维数组的话,我们还得借用指针数组(数组内存储的都是指针类型的数据),下面是事例程序:

    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int *ipArray[2] = {iArray[0], iArray[1]};
    int **pArray = NULL;pArray = ipArray;
    printf("array[0][0] = %d\n", pArray[0][0]);
    printf("array[1][2] = %d\n", pArray[1][2]);
    
    return 0;
    }

     

     


    由于二级指针要跳两次,所以中间还需要额外的存储一级指针的空间。所以一般不建议用二级指针去访问二维数组。

    转载于:https://www.cnblogs.com/wangkangluo1/archive/2012/04/12/2444946.html

    展开全文
  • 指针访问二维数组

    2014-02-10 15:35:05
    之前对数组的概念一直没有理解透彻,只觉得数组名就是个常量指针而已,用法基本的指针差不多。所以当我尝试用二级指针去访问二维数组时,就经常会出错。下面就是刚开始写的个错误的程序: #include int ...

    之前对数组的概念一直没有理解透彻,只觉得数组名就是个常量指针而已,用法和基本的指针差不多。所以当我尝试用二级指针去访问二维数组时,就经常会出错。下面就是刚开始写的一个错误的程序:

    复制代码
    #include <stdio.h>
    
    int main()
    {
            int iArray[2][3] =        {{1,2,3},{4,5,6}};
            int **pArray = NULL;
    
            pArray = iArray;
            
            printf("array[0][0] = %d\n", pArray[0][0]);
            printf("array[1][2] = %d\n", pArray[1][2]);
                    
            return 0;
    }
    复制代码
     

         开始的时候我是这样分析的:本来数组和指针就差不多,一维数组和一维指针对应,那么二维数组名应该和二维指针差不多,所以上面那个程序是没有错的,应该打印出的是1和6。但是当我实际编译运行的时候,却出现了段错误,也就是我访问了不该访问的地址空间。那错误到底出在什么地方呢?正确的程序应该怎么写呢?
         为了解决问题,不得不让我重新理解数组的含义。仔细翻阅一些书籍后,我发现其实数组并不是我原来想象的那么简单:一个常量指针标识的一群变量的集合。数组应该也算是一个完备的变量类型:有名字,有大小,也有地址。只不多就是名字和它的地址一样罢了。也正是因为数组有大小,所以当用sizeof对数组名进行运算时,算出来的是实际数组的大小,而不是指针的大小。
         也正是因为这样,所以指向数组的指针和指向指针的指针也大不一样。它们俩最明显的不同就是表现在指针步进的时候。我们知道指针在进行++运算的时候,跨越的实际地址取决于指针指向的数据类型:对于一般的32位机来说,假如指向的是int型数据,跨越的实际地址就是4,指向的是指针型数据,跨越的实际地址也是4,当指向的是数组类型的时候,跨越的实际地址就是数组的长度了。
         现在再回头分析上面那个错误程序,根据下标引用符号[]的运算规则,我们知道pArray[0][0]其实就是**pArray,而iArray实际上只是个数组变量名,而它的值就是整个数组的开始地址(其实&iArray,iArray,iArray[0]以及&iArray的值都是数组的开始地址,都是在编译过程中编译器赋予的值)。那么其实*pArray就已经是iArray[0][0]的值了,也就是1,而**pArray则是去访问地址为1的地址空间中的数据,自然会出段错误。
         其实用指针访问二维数组可以直接用一级指针就可以了。比如下面这个程序:

    复制代码
    int main()
    {
            int iArray[2][3] =        {{1,2,3},{4,5,6}};
            int *pArray = NULL;
    
            pArray = iArray;
            
            printf("array[0][0] = %d\n", *pArray);
            printf("array[1][2] = %d\n", *(pArray + 1 * 3 + 2));
                    
            return 0;
    }
    复制代码
        因为数组本身在地址空间中就是连续排列的,根据行数和列数,我们自己计算出访问单元的地址偏移量就可以用一级指针轻松遍历二维数组中的所有数据了。
    我们还可以尝试用指向数组的指针来访问二维数组的成员。下面就是事例程序:
    复制代码
    int main()
    {
            int iArray[2][3] =        {{1,2,3},{4,5,6}};
            int (*pArray)[3] = NULL;
    
            pArray = iArray;
            
            printf("array[0][0] = %d\n", pArray[0][0]);
            printf("array[1][2] = %d\n", pArray[1][2]);
                    
            return 0;
    }
    复制代码

         简单分析一下这个程序:我们知道[]运算符的结合方向是由左向右,pArray[1][2]就等价于(* (pArray + 1))[2],而由于pArray是数组指针,而且数组的长度为3,所以* (pArray + 1)就表示iArray[1]这个数组,则pArray[1][2]则就完全等价于iArray[1][2]。
         如果非得想用二级指针来访问二维数组的话,我们还得借用指针数组(数组内存储的都是指针类型的数据),下面是事例程序:

    复制代码
    int main()
    {
            int iArray[2][3] =        {{1,2,3},{4,5,6}};
            int *ipArray[2] = {iArray[0], iArray[1]};
            int **pArray = NULL;
    
            pArray = ipArray;
            
            printf("array[0][0] = %d\n", pArray[0][0]);
            printf("array[1][2] = %d\n", pArray[1][2]);
                    
            return 0;
    }
    展开全文
  •  之前对数组的概念一直没有理解透彻,只觉得数组名就是个常量指针而已,用法基本的指针差不多。所以当我尝试用二级指针去访问二维数组时,就经常会出错。下面就是刚开始写的个错误的程序: #include int ...

    实例分析用指针访问二维数组的几种方法


         之前对数组的概念一直没有理解透彻,只觉得数组名就是个常量指针而已,用法和基本的指针差不多。所以当我尝试用二级指针去访问二维数组时,就经常会出错。下面就是刚开始写的一个错误的程序:

    复制代码
    #include <stdio.h>

    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int **pArray = NULL;

    pArray = iArray;

    printf("array[0][0] = %d\n", pArray[0][0]);
    printf("array[1][2] = %d\n", pArray[1][2]);

    return 0;
    }
    复制代码
    ?
     

         开始的时候我是这样分析的:本来数组和指针就差不多,一维数组和一维指针对应,那么二维数组名应该和二维指针差不多,所以上面那个程序是没有错的,应该打印出的是1和6。但是当我实际编译运行的时候,却出现了段错误,也就是我访问了不该访问的地址空间。那错误到底出在什么地方呢?正确的程序应该怎么写呢?
         为了解决问题,不得不让我重新理解数组的含义。仔细翻阅一些书籍后,我发现其实数组并不是我原来想象的那么简单:一个常量指针标识的一群变量的集合。数组应该也算是一个完备的变量类型:有名字,有大小,也有地址。只不多就是名字和它的地址一样罢了。也正是因为数组有大小,所以当用sizeof对数组名进行运算时,算出来的是实际数组的大小,而不是指针的大小。
         也正是因为这样,所以指向数组的指针和指向指针的指针也大不一样。它们俩最明显的不同就是表现在指针步进的时候。我们知道指针在进行++运算的时候,跨越的实际地址取决于指针指向的数据类型:对于一般的32位机来说,假如指向的是int型数据,跨越的实际地址就是4,指向的是指针型数据,跨越的实际地址也是4,当指向的是数组类型的时候,跨越的实际地址就是数组的长度了。
         现在再回头分析上面那个错误程序,根据下标引用符号[]的运算规则,我们知道pArray[0][0]其实就是**pArray,而iArray实际上只是个数组变量名,而它的值就是整个数组的开始地址(其实&iArray,iArray,iArray[0]以及&iArray的值都是数组的开始地址,都是在编译过程中编译器赋予的值)。那么其实*pArray就已经是iArray[0][0]的值了,也就是1,而**pArray则是去访问地址为1的地址空间中的数据,自然会出段错误。
         其实用指针访问二维数组可以直接用一级指针就可以了。比如下面这个程序:

    复制代码
    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int *pArray = NULL;

    pArray = iArray;

    printf("array[0][0] = %d\n", *pArray);
    printf("array[1][2] = %d\n", *(pArray + 1 * 3 + 2));

    return 0;
    }
    复制代码
        因为数组本身在地址空间中就是连续排列的,根据行数和列数,我们自己计算出访问单元的地址偏移量就可以用一级指针轻松遍历二维数组中的所有数据了。
    我们还可以尝试用指向数组的指针来访问二维数组的成员。下面就是事例程序:
    复制代码
    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int (*pArray)[3] = NULL;

    pArray = iArray;

    printf("array[0][0] = %d\n", pArray[0][0]);
    printf("array[1][2] = %d\n", pArray[1][2]);

    return 0;
    }
    复制代码

         简单分析一下这个程序:我们知道[]运算符的结合方向是由左向右,pArray[1][2]就等价于(* (pArray + 1))[2],而由于pArray是数组指针,而且数组的长度为3,所以* (pArray + 1)就表示iArray[1]这个数组,则pArray[1][2]则就完全等价于iArray[1][2]。
         如果非得想用二级指针来访问二维数组的话,我们还得借用指针数组(数组内存储的都是指针类型的数据),下面是事例程序:
    复制代码
    int main()
    {
    int iArray[2][3] = {{1,2,3},{4,5,6}};
    int *ipArray[2] = {iArray[0], iArray[1]};
    int **pArray = NULL;

    pArray = ipArray;

    printf("array[0][0] = %d\n", pArray[0][0]);
    printf("array[1][2] = %d\n", pArray[1][2]);

    return 0;
    }
    复制代码

         由于二级指针要跳两次,所以中间还需要额外的存储一级指针的空间。所以一般不建议用二级指针去访问二维数组。

    展开全文
  • 将一个字符数组进行遍历:  while(*src !='\0')  {  src++; ... 这里的数组名用法指针的用法基本差不多,但是它们还是有区别的。... 数组名代表的是这个数组的首元素的地址(任何元素,包括一维数组
  • 如果在无下标表达式中使用一维数组,组名计算为指向该数组中的第一个元素的指针。 // using_arrays.cpp int main() { char chArray[10]; char *pch = chArray; // Evaluates to a pointer to the first element...
  • 目录数组和指针的区别一维整型数组sizeof的基本用法二维整形数组字符数组 数组指针的区别 (1) 指针保存的是数据的地址。 数组是用来保存数据的。 (2) 指针访问数据 是通过数据的地址进行解引用,间接访问的。...
  • 数组名和数组指针

    2016-10-29 22:40:37
    将一个字符数组进行遍历:  while(*src !='\0')  {  src++; ... 这里的数组名用法指针的用法基本差不多,但是它们还是有区别的。... 数组名代表的是这个数组的首元素的地址(任何元素,包括一维数组
  • 指针与数组指针一维数组指针与二维数组指针与多维数组三.指针使用常见错误四.常指针五.函数指针六.指针数组七.数组指针八.指针与引用九.指针与结构体十.附基本用法C语言中指针存储地址打印与使用:不同平台(64位,...
  • 指针专题

    2020-08-03 18:35:41
    指针专题_华清远见_小美老师指针专题一指针的基本用法指针的运算指针与数组指针与二维数组指针专题二字符指针与字符串指针数组多级指针void指针与const修饰符 指针专题 指针的基本用法 掌握指针的基本用法,我学习...
  • 指针和一维数组2.2. 指针变量的运算2.3. 指针数组和数组指针3. 指针和结构体4. 指针和函数4.1. 什么是函数指针4.2. 函数指针的作用4.3. 函数指针的用法5. 多级指针四、void*指针的妙用五、动态内存分配和释放1. ...
  • 本书从介绍内存和实时内存概念开始,然后讲述了指针变量的概念和它重要的操作(引用和解引用)、指针运算和一维数组、使用指针处理字符串、指针访问多维数组的用法、使用指针访问结构体与成员字段、函数指针概念的...
  • Python3科学计算库numpy的基本用法

    千次阅读 2018-04-17 21:19:15
    标准安装Python中用列表(名单)保存组值,可以用来当作数组使用,不过由于列表元素...NumPy诞生弥补了这些不足,NumPy提供了两种基本的对象:ndarray(N维数组对象)是存储单一数据类型多维数组,ufunc...
  • 数组名 与 数组名数组指针的使用数组参数一维数组传参练习题 字符指针 基本知识 int main() { char p = 'a'; printf("%c\n",p); //a printf("%d\n",p); //97 system("pause"); return 0; } 计算机只认识二进制...
  • 第六节--指针专题

    2020-07-20 17:40:44
    掌握指针的基本用法 指 针: C程序设计中使用指针可以 使程序简洁、紧凑、高效、 有效地表示复杂的数据结构 动态分配内存 得到多于个的函数返回值 地址和变量: 指针变量的说明: 一般形式如下: <...
  • 指针

    2018-05-01 15:58:44
    掌握用指针访问变量和一维数组的方法3.掌提用指针访问二维数组的方法4.掌握用指针处理字特串的方法。5.掌握指针数组的使用方法。6.热悉函数指针以及返回指针函数的用法。1指针的基本概念1.1内存、地址和指针1.内存...
  • 《指针的艺术》主要探讨C语言指针的基本概念及其与变量、数组、结构体和文件之间的应用,同时剖析C++、C++/CLR、Java、Visual C#及Visual Basic中的引用(Reference),并分别以指针和引用(Reference)实现链表、堆栈与...
  • 展开全部居然 整个楼里面都答非所问了 看我62616964757a686964616...可以等同于Object[] obj一维数组理解的数组本质是连续的指针地址 其中数组的头指针是必须的 但是二者的不同在于何处呢?很明显Obj...是针对方法传...
  • 计算机科学与技术系 C语言实验报告 实验名称指针及其应用 日期 得分 指导老师: 专业 班次 姓名 学号 实验目的 掌握变量的指针及其基本用法 掌握一维数组的指针及其基本用法 掌握指针变量作为函数的参数时参数的传递...
  • 计算机科学与技术系 C 语言实验报告 实验名称指针及其应用 日期 得分 指导老师 专业 班次 姓名 学号 实验目的 1 掌握变量的指针及其基本用法 2 掌握一维数组的指针及其基本用法 3 掌握指针变量作为函数的参数时参数...
  • 计算机科学与技术系 C 语言实验报告 实验名称指针及其应用 日期 得分 指导老师 专业 班次 姓名 学号 实验目的 1 掌握变量的指针及其基本用法 2 掌握一维数组的指针及其基本用法 3 掌握指针变量作为函数的参数时参数...
  • 首先介绍一下它相关知识及其基本用法: 1、相关知识: (1)首先使用它必须包含头文件#include (2)创建vector对象:一维的:vector vec ,二维:vector vec。 (3)使用下标访问元素,cout (4)使用迭代访问...
  • 一.new 几种基本用法 1.创建一个动态变量  int *p;  p=new int; //new int 操作时在堆区产生一个int型动态变量,结果为该动态变量地址(或指针)。... // 操作在程序堆区中产生一个动态的一维数组,数组
  • 嵌入式day3

    2018-07-18 22:24:08
    今日学习任务  gcc编译器基本用法、c数据类型、数组、函数 今日任务完成情况  1.... ... 2编程实现整型一维数组排序(冒泡排序、改进冒泡排序) ... 3.... 4.二维数组的指针、列指针遍历数组。 ...
  • 30) C语言之一维数组的使用 31) C语言之二维数组和多维数组 32) C语言之指向数组的指针 33) C语言之保护数组内容const的使用 34) C语言之指向多维数组的指针 函数 35) C语言之函数的定义和调用 36) C语言之定义...
  • 143_指针_23_动态内存分配举例_动态一维数组的构造 142_指针_22_malloc函数的用法2 141_指针_21_malloc函数使用的简单介绍 140_指针20_为什么需要动态分配内存【重点】 139_指针19_传统数组的缺点【重点】 138_指针...

空空如也

空空如也

1 2 3
收藏数 42
精华内容 16
关键字:

一维数组的指针的基本用法