之前有写过一篇叫c++中动态数组的使用,今来看看c++中的字符指针数组的使用。

涛哥:c++中的动态数组使用​zhuanlan.zhihu.com

指针数组,就指向指针的指针,很早以前在说指针的时候说过,但后来发现很多人还是比较难以理解,这一次我们再次仔细说一说指向指针的指针。

先看下面的代码,注意看代码中的注解:

#include <iostream>
#include <string>
using namespace std;  void print_char(char* array[],int len);//函数原形声明  void main(void)
{
//-----------------------------段1-----------------------------------------  char *a[]={"abc","cde","fgh"};//字符指针数组  char* *b=a;//定义一个指向指针的指针,并赋予指针数组首地址所指向的第一个字符串的地址也就是abc0字符串的首地址  cout<<*b<<"|"<<*(b+1)<<"|"<<*(b+2)<<endl;
//-------------------------------------------------------------------------  //-----------------------------段2-----------------------------------------  char* test[]={"abc","cde","fgh"};//注意这里是引号,表示是字符串,以后的地址每加1就是加4位(在32位系统上)  int num=sizeof(test)/sizeof(char*);//计算字符串个数  print_char(test,num);  cin.get();
//-------------------------------------------------------------------------
}  void print_char(char* array[],int len)//当调用的时候传递进来的不是数组,而是字符指针他每加1也就是加上sizeof(char*)的长度
{  for(int i=0;i<len;i++)  {  cout<<*array++<<endl;  }
}

下面我们来仔细说明一下字符指针数组和指向指针的指针,段1中的程序是下面的样子:

char *a[]={"abc","cde","fgh"};
char* *b=a;
cout<<*b<<"|"<<*(b+1)<<"|"<<*(b+2)<<endl;

  char *a[]定义了一个指针数组,注意不是char[], char[]是不能同时初始化为三个字符的,定义以后的a[]其实内部有三个内存位置,分别存储了abc0,cde0,fgh0,三个字符串的起始地址,而这三个位置的内存地址却不是这三个字符串的起始地址,在这个例子中a[]是存储在栈空间内的,而三个字符串却是存储在静态内存空间内的const区域中的,接下去我们看到了char* *b=a;这里是定义了一个指向指针的指针,如果你写成char *b=a;那么是错误的,因为编译器会返回一个无法将char* *[3]转换给char *的错误,b=a的赋值,实际上是把a的首地址赋给了b,由于b是一个指向指针的指针,程序的输出cout<<*b<<"|"<<*(b+1)<<"|"<<*(b+2)<<endl;

结果是:

abc
cde
fgh

  可以看出每一次内存地址的+1操作事实上是一次加sizeof(char*)的操作,我们在32位的系统中sizeof(char*)的长度是4,所以每加1也就是+4,实际上是*a[]内部三个位置的+1,所以*(b+1)的结果自然就是cde了,我们这时候可能会问,为什么输出是cde而不是c一个呢?答案是这样的,在c++中,输出字符指针就是输出字符串,程序会自动在遇到0后停止.

  我们最后分析一下段2中的代码,段2中我们调用了print_array()这个函数,这个函数中形式参数是char *array[]和代码中的char *test[]一样,同为字符指针,当你把参数传递过来的时候,事实上不是把数组内容传递过来,test的首地址传递了进来,由于array是指针,所以在内存中它在栈区,具有变量一样的性质,可以为左值,所以我们输出写成了,cout<<*array++<<endl;当然我们也可以改写为cout<<array[i]<<endl,这里在循环中的每次加1操作和段1代码总的道理是一样的,注意看下面的图!

 下面是内存结构示意图:

到这里这两个非常重要的知识点我都说完了,说归说,要想透彻理解希望读者多动手,多观察,熟能生巧。

备注:

于作者水平,难免有理解和描述上有疏漏或者错误的地方,欢迎共同交流;部分参考已经在正文和参考文献中列表注明,但仍有可能有疏漏的地方,有任何侵权或者不明确的地方,欢迎指出,必定及时更正或者删除;文章供于学习交流,转载注明出处。

共享内存中使用指针_详解c++中字符指针数组的使用相关推荐

  1. python中index函数_详解python中的index函数用法

    1.函数的创建 def fun(): #定义 print('hellow') #函数的执行代码 retrun 1 #返回值 fun() #执行函数 2.函数的参数 普通参数 :要按照顺序输入参数 de ...

  2. python中squeeze函数_详解pytorch中squeeze()和unsqueeze()函数介绍

    squeeze的用法主要就是对数据的维度进行压缩或者解压. 先看torch.squeeze() 这个函数主要对数据的维度进行压缩,去掉维数为1的的维度,比如是一行或者一列这种,一个一行三列(1,3)的 ...

  3. java中parent结构_详解java中继承关系类加载顺序问题

    详解java中继承关系类加载顺序问题 实例代码: /** * Created by fei on 2017/5/31. */ public class SonClass extends ParentC ...

  4. java中this.getclass()_详解java中this.getClass()和super.getClass()的实例

    详解java中this.getClass()和super.getClass()的实例 前言: 遇到this.getClass()和super.getClass()的返回值感到疑惑,经过探索豁然开朗. ...

  5. python中延时函数_详解python中实现延时回调普通函数

    这篇文章主要给大家介绍了关于python中实现延时回调普通函数的相关资料,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧. 前言 ...

  6. python中递归函数写法_详解python中递归函数

    函数执行流程 def foo1(b,b1=3): print("foo1 called",b,b1) def foo2(c): foo3(c) print("foo2 c ...

  7. python中 的用法_详解python中@的用法

    python中@的用法 @是一个装饰器,针对函数,起调用传参的作用. 有修饰和被修饰的区别,@function作为一个装饰器,用来修饰紧跟着的函数(可以是另一个装饰器,也可以是函数定义). 代码1 结 ...

  8. 详解python中的用法_详解python中@的用法

    python中@的用法 @是一个装饰器,针对函数,起调用传参的作用. 有修饰和被修饰的区别,作为一个装饰器,用来修饰紧跟着的函数(可以是另一个装饰器,也可以是函数定义). 代码1 def funa(d ...

  9. mysql中groupby用法_详解SQL中GroupBy的用法

    GROUP BY 语句用于结合合计函数,根据一个或多个列对结果集进行分组. 1.概述 "Group By"从字面意义上理解就是根据"By"指定的规则对数据进行分 ...

最新文章

  1. 公司间STO的Invoice处理
  2. DSP集成开发工具CCS的Git工具使用说明(三)
  3. JavaScript进阶系列01,函数的声明,函数参数,函数闭包
  4. git commit —amend_Git之修改commit记录
  5. Clojure语法学习-循环
  6. 玩转springboot:整合mybatis实例
  7. 关闭或开启memory_target
  8. 关于codeblocks插件(持续更新)
  9. 面向对象也可以搞单片机!
  10. 抢先试用ReSharper UnitRun™ 1.0
  11. starima与arima 预测_38-一些预测模型与方法简介(ARIMA、指数平滑等)
  12. XSS-Game level 9
  13. 互联网时代,还有闷声发大财的吗?
  14. http://www.jb51.net/article/51934.htm
  15. c++gdal如何在大图像中截取小图像并获取其图像信息_如何模拟不规则形状并构建几何模型
  16. python开发接口
  17. Spring的注解@Autowired和@Resource的区别
  18. 整体大于部分_整体叶盘球头鼓锥形铣刀五轴加工技术
  19. 最新最火最流行的抖音火山上热门技术!
  20. web安全训练和教学光盘 – GameOver

热门文章

  1. 前端学习(781):格式化日期年月日星期
  2. 前端学习(660):比较运算符
  3. 前端学习(581):使用element调试dom 查看和调试dom节点
  4. 前端学习(381):CSS3 的视口单位vw、vh实现自适应(带有px,em,rem的简单介绍)
  5. 第二十一期:拜托!面试不要再问我Spring Cloud底层原理
  6. java学习(50):子类继承会优先调用父类的构造器
  7. router-link
  8. jQuery使用ajax传输xml文档在IE中无法正确解析的问题
  9. jboss eap 6.2 ear包 下使用log4j日志
  10. Linux下MySQL 安装配置