指针(2):关于数组指针和指向数组指针的指针及其new
来源:互联网 发布:windows窗口 编辑:程序博客网 时间:2024/05/02 07:53
今天在CSDN上看到了wp123456xt对我很久以前的一篇文章——方正面试的题-找出字符串最多的分解方法http://blog.csdn.net/shizhixin/article/details/4742687的评论,很高兴有人能够提出问题,正好今天有时间,所以回复了。
后来在wp123456xt的CSDN的博文上看到他的一篇求助文章——数组指针问题(求指教),http://blog.csdn.net/wp123456xt/article/details/7021496,也无人回答,闲来无事,就一一解释下吧,这些理解都属于一家之见,也许其中的一些理解上会有问题,还希望大家指出,共同进步嘛。
相关主程序和ex小例子代码可以在我的资源中下载:http://download.csdn.net/detail/shizhixin/3892608
- #include<iostream>
- using namespace std;
- int main()
- {
- float(**q)[5];
- float a[1][5]={{1,2,3,4,5}};
- q=&new float [1][5];//编译可以通过
- //q=&a;//编译通不过
- //q=new float*;//此处我原本想先给q分配一个内存空间,用于存取二维数组a的地址
- //却找不到合适的数据类型
- *q=a;
- for(int i=0;i<5;i++)
- {
- cout<<*(**q+i)<<endl;
- printf("%p\n",**q+i);
- }
- cout<<endl;
- cout<<&q<<endl;
- return 0;
- }
#include<iostream>using namespace std;int main(){float(**q)[5];float a[1][5]={{1,2,3,4,5}};q=&new float [1][5];//编译可以通过//q=&a;//编译通不过//q=new float*;//此处我原本想先给q分配一个内存空间,用于存取二维数组a的地址//却找不到合适的数据类型*q=a;for(int i=0;i<5;i++){cout<<*(**q+i)<<endl;printf("%p\n",**q+i);}cout<<endl;cout<<&q<<endl; return 0;}
/*
一一解析你的代码,你的代码用--标志的行
--float(**q)[5];
这里定义的q,是一个指向(数组指针)的指针,本质上它是一个二级指针,他的下一级是一个指向[5]大小的
数组的指针,最终才是一个二维的数组类型;如下图,如果真正理解了这个,基本上后面的就不难理解了;
--float a[1][5]={{1,2,3,4,5}};
a当然是一个1*5的二维数组;
--q=&new float [1][5];//编译可以通过
这句话可以拆分开来看,就比较容易理解为什么能编译通过了,拆分如下:
float (*b)[5] = new float[1][5]; //b是一个数组指针,指向了一个新开辟的数组,这个肯定没问题吧
q=&b; //用一个二级指针,就是指向(数组指针b)的指针即q,这样q这个指针里存储b的地址,这个当然是可以的啊。
如果还不理解的话看下面这段:
- ex1:
- int ** pa; //相当于q
- int *pb; //相当于b
- int n=10; //相当于a
- pb=&n;
- pa=&pb;//这样没编译肯定没问题吧,并且**pa,*pb的值应该和n的值都相等吧。
ex1:int ** pa; //相当于qint *pb; //相当于bint n=10; //相当于apb=&n; pa=&pb;//这样没编译肯定没问题吧,并且**pa,*pb的值应该和n的值都相等吧。
--//q=&a;//编译通不过
自然,上面那个例子,pa=&n,这样可以么??
-- //q=new float*;//此处我原本想先给q分配一个内存空间,用于存取二维数组a的地址
-- //却找不到合适的数据类型
如果只是仅仅为了暂时存储二维数组a的地址方便操作二维数组之用,没必要new一个内存空间,如上面的代码中
pa也没有去new一个空间来存储a的地址,程序会自动在编译系统就为已定义的变量分配相应的内存单元的。
退一步说,如果你一定要new,比如同时操作多个,那应该怎么new呢,还是上面那个例子,
int * pb = new int;
int ** pa = new int*;
应该这么new吧,也就是定义的这个pb指针,他指向new的存储区的数据类型是int型的,同样,pb指向的是int*的
数据类型,那new的话应该new int*;所以对于我们的float(**q)[5],q开始说了是指向(数组指针b)的指针,而
b的类型是float (*b)[5],所以应该这么new:float(**q)[5] = new (float(*)[5]);如果你想同时new n个这样
指向数组指针的指针,那就int(**q)[5]=new (int(*[n])[5]); 不过这里释放的时候要注意,和new二维数组一样,
要先delete [] p[0--n];然后再delete [] p;例如:
- ex2:
- int(**p)[2]=new (int(*[3])[2]);//注意new后面的括号
- p[0]=new int[2][2];
- p[1]=new int[2][2];
- p[2]=new int[2][2];
- delete [] p[0];
- delete [] p[1];
- delete [] p[2];
- delete [] p;
- int(**q)[2]=new (int(*)[2]);//一个的情形
- delete []q;
ex2:int(**p)[2]=new (int(*[3])[2]); //注意new后面的括号p[0]=new int[2][2]; p[1]=new int[2][2]; p[2]=new int[2][2]; delete [] p[0]; delete [] p[1]; delete [] p[2]; delete [] p;int(**q)[2]=new (int(*)[2]); //一个的情形delete []q;
-- // *q=a;
编译上是可以通过的,毕竟相当于第一个例子中*pa=&n(*pa=pb,pb=&n),这里a也是代表其首地址,
但是需要注意的一个问题,直接把a的值赋予*q,*q所代表的是q所指向的内容,
而如果开始q指向哪里了都没定义,这样肯定编译没问题,但是程序运行有问题的。换句话说,如果程序如下:
- ex3-1:
- float(**q)[5];
- float a[1][5]={{1,2,3,4,5}};
- *q=a;//能编译但这样是有问题的!!
- ex3-2:
- float(**q)[5];
- float a[1][5]={{1,2,3,4,5}};
- q=&new float [1][5];
- *q=a;//编译能通过,并且赋值也是正确的
ex3-1:float(**q)[5];float a[1][5]={{1,2,3,4,5}};*q=a;//能编译但这样是有问题的!!ex3-2:float(**q)[5];float a[1][5]={{1,2,3,4,5}};q=&new float [1][5];*q=a;//编译能通过,并且赋值也是正确的
-- for(int i=0;i<5;i++)
-- {
-- cout<<*(**q+i)<<endl;
-- printf("%p\n",**q+i);
-- }
-- cout<<endl;
-- cout<<&q<<endl;
这段代码应该不难理解,但是也需要注意的一个地方是
**q是获取a的首地址里面的内容,
**q+i是获取a的首地址然后偏移i个float单位,注意这里的偏移单位和数组指针直接+1不一样,这里是q
先获得首地址,然后偏移i个单位,通过下面这个例子慢慢体会:
- ex4:
- float a[2][5]={{1,2,3,4,5},{7,8,9,0,1}};
- float (*b)[5];
- b=a;
- for (int i=0;i<2;i++)
- {
- cout<<**(b+i)<<endl; //output: 1,7
- cout<<**b+i<<endl; //output:1,2
- }
ex4:float a[2][5]={{1,2,3,4,5},{7,8,9,0,1}};float (*b)[5];b=a;for (int i=0;i<2;i++){cout<<**(b+i)<<endl; //output: 1,7cout<<**b+i<<endl; //output:1,2}
0 0
- 指针(2):关于数组指针和指向数组指针的指针及其new
- 关于数组指针和指向数组指针的指针及其new
- 指针数组,和指向指针的指针
- 指针数组和指向指针的指针
- 指针数组和指向指针的指针
- 数组指针和指向指针的指针
- 关于指针数组 数组指针 函数指针 函数指针数组 指向函数指针数组的指针
- 指向数组的指针和指针数组
- 指针数组和指向指针的数组
- 指针数组和指向数组的指针
- 数组指针、 指针数组、函数指针、函数指针数组和指向函数指针数组的指针
- 指针函数、数组指针、函数指针、函数指针数组和指向函数指针数组的指针
- 关于指针的一些知识,记多维数组指针、指针数组、指针的指针和指向函数的指针
- 指针、数组指针、指针数组、指向指针的指针
- 关于指向数组的指针
- 指向指针数组的指针
- 二维数组和指向指针的指针
- 二维数组和指向指针的指针
- 《浪潮之巅》5奔腾的芯 英特尔公司
- 算法分析-选择排序(直接选择排序 & 堆排序)
- Bose起诉苹果旗下Beats专利侵权,结果如何?
- java面向对象-子父类中函数的特点-覆盖
- spring中的邮件发送
- 指针(2):关于数组指针和指向数组指针的指针及其new
- 《浪潮之巅》6IT领域的罗马帝国---微软公司
- 算法分析-插入排序(直接插入排序 & 希尔排序)
- 指针(3):理解一般指针和指向指针的指针
- [高斯消元求期望] zjutoj 1423 地下迷宫
- ArrayList方法摘要
- Android中Context详解 ---- 你所不知道的Context
- 指针(4):指针数组和数组指针的区别
- poj 1698 二部图多重最大匹配(拍电影)