二维数组和指向指针的指针

引用地址: http://www.cnblogs.com/stoneJin/archive/2011/09/21/2184211.html

一道面试题引发的问题,首先要知道[]的优先级高于*,题目:

char **p,a[6][8]; 问p=a是否会导致程序在以后出现问题?为什么?

直接用程序说明:

#include<stdio.h>

void main(){    char **p,a[6][8];    p = a;    printf("\n");}

编译,然后就会发现通不过,报错:错误 1 error C2440: “=”: 无法从“char [6][8]”转换为“char **”

于是乎,我看了下《C专家编程》里10.5节—使用指针向函数传递一个多维数组。

方法一,函数是 void fun(int arr[2][3]); 这种方法只能处理2行3列的int型数组。

方法二,可以省略第一维的长度。函数是 void fun(int arr[][3]);这种方式虽然限制宽松了一些,但是还是只能处理每行是3个整数长度的数组。

    或者写成这种形式 void fun(int (*arr)[3]);这是一个数组指针或者叫行指针,arr和*先结合使得arr成为一个指针,这个指针指向具有3个

    int类型数据的数组。

方法三,创建一个一维数组,数组中的元素是指向其他东西的指针,也即二级指针。函数是 int fun(int **arr);这种方法可以动态处理各行各列不一样长度的数据。

注意:只有把二维数组改成一个指向向量的指针数组的前提下才可以这么做!比如下面的程序可以正常输出abc:

#include <iostream> using namespace std; void test(char **ptr) {     cout << *ptr << endl; } 

int main() {     char *p[3] = {"abc", "def", "ghi"};     test(p);     return 0; }

在《C专家编程》10.3节的小启发里讲的很透彻:(以下这段文字及对比一定要认真分析!)

数组和指针参数是如何被编译器修改的?

数组名被改写成一个指针参数”规则并不是递归定义的。数组的数组会被改写成“数组的指针”,而不是“指针的指针”:

实参                                                      所匹配的形参

数组的数组          char c[8][10];                 char (*)[10];          数组指针

指针数组             char *c[10];                   char **c;               指针的指针

数组指针(行指针)  char (*c)[10];                 char (*c)[10];        不改变

指针的指针           char **c;                       char **c;               不改变

下面再看一个网友的一段分析相当给力的代码:

#include "stdafx.h" #include <iostream> using namespace std; 

int _tmain(int argc, _TCHAR* argv[]) {     int arr1[3];     int arr2[3];     int arr3[3];     int * ptr;     // ptr1是一个指向 int [3] 的指针,即ptr的类型和&arr1的类型是一样的,注意:arr1指向的内存区域定长     int ptr1[3][3]={{1,2,3},{1,2,3},{1,2,3}};     // ptr2是一个指向 int * 的指针,即ptr2的类型和&ptr是一样的,注意:ptr指向的内存区域不定长     int * ptr2[3]={arr1,arr2,arr3};     // ptr3是一个指向 int [3] 的指针,即ptr3的类型和&arr1的类型是一样的,注意:arr1指向的内存区域定长     int(* ptr3)[3]=&arr1;     ptr3=ptr1; // 没错,他们的类型相同  // ptr3=ptr2;//error 无法从“int *[3]”转换为“int (*)[3]  // ptr4是一个指向 int * 的指针,即ptr4的类型和&ptr是一样的,注意:ptr指向的内存区域不定长     int ** ptr4;     //ptr4=&arr1; //error 无法从“int (*)[3]”转换为“int **     ptr4=ptr2; // 没错,他们的类型相同  //ptr4=ptr3; // error 无法从“int (*)[3]”转换为“int **     return 0; }

时间: 2024-10-12 13:55:10

二维数组和指向指针的指针的相关文章

一维数组,二维数组,三维数组,数组与指针,结构体数组,通过改变指针类型改变访问数组的方式

 打印数组中的每个元素,打印每个元素的地址: #include <stdio.h> #include <stdlib.h> void main(void) { int a[10] = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10 }; for (int *p = a; p < a + 10;p++)  //指针类型决定4个字节 { printf("\n%p,%d", p, *p); } getchar(); } 指针数组 #inclu

二维数组指针及二维动态数组的分配问题

在我以前的文章中都有讲过关于数组指针及指针数组的相关问题,但是讲得不够深入,我后来后了别人写的博客后觉得人家的确实写得好, 也学到了不少东西,对以前的问题有深的领悟了,于是准备结合这些博客和文章再稍微深入一点讲讲这些问题.这些指针的问题是C语言中的基础与关键 而且一旦出现这些问题,不太好找bug的来源,有时候不得不借助反汇编. 参考文章: http://c.biancheng.net/cpp/html/476.html       C语言指针数组和数组指针 http://blog.csdn.ne

例看二维数组,指针,二维数组指针

例程: /****************************************************** * * 文件名:例程 * * 文件描述:例看二维数组,指针,二维数组指针 * * 创建人:Jesse * * 版本号: * * 修改记录: * ******************************************************/ #include <stdio.h> #define ROW 3 #define LINE 3 void main(voi

二维数组和二级指针关系浅析

昨天写了关于一级指针的见解,即二级数组的用法和二级指针差不多,关于数组指针和指针数组这两个是不同的概念,这一点我们一定要清楚: 数组指针我们可以理解为指向数组的指针,就是一个指针: 指针数组则可以理解为数组里存的是指针,即每个储存空间上储存的是指针变量:这里储存了多个指针 一个数组可以这样定义 char a[3];分配了3个字节的内存 二维数组可以这样定义 char b[3][3];分配了3*3 即9个字节的内存 我们知道一维数组和一级指针的用法差不多,那么二级指针有和二级指针有什么关系呢? {

二维数组和指针

二维数组和指针⑴ 用指针表示二维数组元素.要用指针处理二维数组,首先要解决从存储的角度对二维数组的认识问题.我们知道,一个二维数组在计算机中存储时,是按照先行后列的顺序依次存储的,当把每一行看作一个整体,即视为一个大的数组元素时,这个存储的二维数组也就变成了一个一维数组了.而每个大数组元素对应二维数组的一行,我们就称之为行数组元素,显然每个行数组元素都是一个一维数组 下面我们讨论指针和二维数组元素的对应关系,清楚了二者之间的关系,就能用指针处理二维数组了.设p是指向数组a的指针变量,若有:p=a

二维数组名和二级指针

1. 指针 1.1 一个指针包含两方面:a) 地址值:b) 所指向的数据类型. 1.2 解引用操作符(dereference operator)会根据指针当前的地址值,以及所指向的数据类型,访问一块连续的内存空间(大小由指针所指向的数据类型决定),将这块空间的内容转换成相应的数据类型,并返回左值. 有时候,两个指针的值相同,但数据类型不同,解引用取到的值也是不同的,例如, 1 char str[] ={0, 1, 2, 3}; /* 以字符的ASCII码初始化 */ 2 3 char * pc

c语言中如何通过二级指针来操作二维数组

通过二级指针去访问二维数组需要先给二级指针分配等同于二维数组行数的一维数组指针,然后把二维数组的每行首地址赋值给对应位置的一维指针上.之后就可以通过二维指针直接访问了. 参考代码如下,可以看具体注释辅助理解. 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 #include <stdio.h>//输入输出头文件. #include <stdlib.h>//本程序需要用到malloc/free函数,引

参数传递二维数组

转自http://blog.csdn.net/yunyun1886358/article/details/5659851 数组名作为形参 1 void func1(int iArray[][10]) 2 { 3 4 } 5 6 7 8 int main() 9 { 10 int array[10][10]; 11 func1(array); 12 13 } 编译通过,注意形参声明一定要给出第二个维度的大小,要不编译不过. 一维数组指针作为形参 1 void func2(int (*pArray)

二维数组知多少

有的实际问题一维数组是无法解决的,所以引入二维数组甚至是多维数组,这里着重讨论一下二维数组,如果深刻理解二维数组多维数组也就迎刃而解. 1. 二维数组的定义:例如现在有3支球队,每支队有5个人,要充分表达每个人便可以引入二维数组,例如a[0][0]就表示第一支队伍的第一个人.这里的a便是数组名,第一个[0]表示第一支队伍,第二个[0]表示第一支队伍里的第一个人.根据此类比喻可以根据条件要求将二维数组扩展为多维数组. 2. 二维数组在内存中布局:我们可以把二维数组的布局想象成表格,第一行表格便是第