简洁既是美—用while语句复制数组

简洁既是美,程序员应尽量尝试编写简洁的表达式,争取用简单的代码来实现更多的功能,当然,这也要看情况了(有时候也得考虑程序运行的时间嘛)。

在阅读C++Prime Plus到while语句时有一个讲一个数组内容复制到另一个数组的例子:

//arr1 is an array if ints

int *source=arr1;

size_t sz=sizeof(arr1)/sizeof(*arr1); //number of elements

int *dest=new int[sz];

while(source!=arr1+sz)

*dest++=*source++;  //copy element and increment pointers

首先初始化source和dest,并使他们各自指向所关联的数组的第一个元素。while循环条件判断是否已经到达要复制的数组的末尾。如果没有,继续执行循环。循环体只有单个语句,实现元素的复制,并对两个指针做自增操作,使他们指向对应数组的下一个元素。
此处,循环体中的语句:

*dest++=*source++;

即所说的简约。这个表达式也等价于:

{

*dest=*source;

++dest;

++source;

}
根据上述,我在编译器上编写了下面的程序:

#include<iostream>

using namespace std;

int main(){

char arr1[]="string";

char* source=arr1;

size_t sz=sizeof(arr1)/sizeof(*arr1);

char *dest=new char[sz];

while(source!=arr1+sz)

*dest++=*source++;

cout<<arr1<<endl;

cout<<dest<<endl;

cout<<"**********"<<endl;

cout<<sz<<endl;

delete []dest;

return 0;

}
程序的作用为将数组arr1复制到dest中,并输出arr1和dest。但运行的结果并不是我想的:
问题

首先,我想到的是是不是数组arr1中的内容并没有复制到dest中,所以我对程序进行了但步跟踪,最后找到了原因:

开始,我们定义了一个arr1数组,接着使用new表达式动态创建了一个数组,并返回了指向新创建对象的指针dest,接着利用source指针和
dest指针复制了元素,这看起来并没有错。但是我忽略了一点,dest是一个指向动态数组的指针而不是数组名,可是我在最后的输出时把dest指针当做
了数组名(cout<<dest<<endl;)。
让我们来看看C++ Prime Plus上是怎么描述new表达式的:new表达式动态创建对象时,只需指定其数据类型,而不必为该对象命名,取而代之的是,new表达式返回指向新创建对象的指针,我们通过该指针来访问此对象。
虽然我最后输出时的确是使用dest指针来访问我们创建的动态数组,但需要知道的是此时的dest指针指的已经不是动态数组了。
如图,在程序执行while循环之前,source和dest指针分别指向arr1和动态数组的第一个元素,但执行了while循环后两个指针如图所示,所以此时再利用dest指针来访问动态数组是不行了。

解决方法:就像书上说的,对于new表达式动态创建的对象,我们通过返回的指针来访问此对象,而在本例中dest指针充当了工作指针,从而使得dest指针最后并没有指向动态数组,这样给我们访问动态数组不方便,所以我们可以再创建一个指针来代替dest指针充当工作指针。
程序更给如下:

//…

char *dest=new char[sz];

char *dest_p=dest;

while(source!=arr1+sz)

*dest_p++=*source++;

//….
程序运行结果如下:

总结:

1、简洁既是美,作为一个程序员应尽量做到自己编写的程序短小精悍,以比较少的代码使用更大的功能,有经验的程序员非常重视简练。要不断研究类似*dest++=*source++;的代码,最后达到一目了然的地步。

2C++中,在使用new表达式创建动态对象时,我们会利用返回的指针来访问此对象,所以应该创建一个新的指针来充当工作指针,避免原指针最后知道我们不清楚的地方而对访问此对象造成麻烦。

时间: 2024-10-11 06:56:42

简洁既是美—用while语句复制数组的相关文章

【简洁之美】裴波那切数列生成器 python

裴波那切数列可以用生成器较好的去生成,直接上代码: # 1 控制最大数字版本def fib(max): x,y = 0,1 while y < max: yield x x,y = y,x+y print [x for x in fib(100)] # 输出[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55] # 2 控制迭代个数版本 def fib(count): x,y,n = 0,1,1 while n < count: yield x x,y = y,x+y n

bash编程 :if,case语句

bash之条件判断(选择执行) 单分支if语句: if CONDITION; then if-true-分支 fi 示例:写一个脚本,如果文件不存在,就创建文件 #!/bin/bash # file=/root/fstab   if [ ! -f $file ]; then   touch $file fi 双分支if语句: if CONDITION; then if-true-分支 else if-true-分支 fi 示例:写一个脚本,如果文件不存在,就说文件不存在,并创建文件 #!/bin

「8」条件语句

1.简单if语句 ●语法 if.else属于条件分支语句 if (条件) { ←条件表达式或逻辑表达式 //语句1 ←条件成立:执行语句1 } else { //语句2 ←条件不成立:执行语句2 } ●要点 程序流程有三: ●顺序执行 ●选择执行 ●循环执行 条件分支语句用于选择执行.可以只有单独if语句而没有else语句.当if语句块中只有一条指令的时候,可以省略大括号(不推荐使用,尽量使用大括号).if-else语句可以嵌套. ●流程图 ●条件表达式(简化的if-else语句) 条件表达式由

L7.1 linux shell 条件判断与循环语句

bash脚本条件判断语句详细使用 条件判断的使用方法及其相关示例: 本文对bash中test语句,if判断语句(单分支,多分支)case语句详细说明,如下 条件测试:test 作用:Shell中的test命令用于检查某个条件是否成立,它可以进行数值.字符和文件三个方面的测试. test使用语法 test EXPRESSION 也可以使用 :[ EXPRESSION ]:[[ EXPRESSION ]] 整数测试: 隐含着做数值大小比较,所以不要给变量引用加引用: $A -gt $B:是否大于:是

华为C语言编程规范

DKBA华为技术有限公司内部技术规范DKBA 2826-2011.5C语言编程规范2011年5月9日发布 2011年5月9日实施华为技术有限公司Huawei Technologies Co., Ltd.版权所有 侵权必究All rights reserved密级:confidentiality levelDKBA 2826-2011.52011-06-02 华为机密,未经许可不得扩散 Huawei Confidential 第2页,共61页Page 2 , Total61修订声明Revision

Linux应用环境实战10:Bash脚本编程语言中的美学与哲学(转)

阅读目录 一.一切皆是字符串 二.引用和元字符 三.字符串从哪里来.到哪里去 四.再加上一点点的定义,就可以推导出整个Bash脚本语言的语法了 五.输入输出重定向 六.Bash脚本语言的美学:大道至简 总结: 我承认,我再一次地当了标题党.但是不可否认,这一定是一篇精华随笔.在这一篇中,我将探讨Bash脚本语言中的美学与哲学. 这不是一篇Bash脚本编程的教程,但是却能让人更加深入地了解Bash脚本编程,更加快速地学习Bash脚本编程. 阅读这篇随笔,不需要你有Bash编程的经验,但一定要和我一

为何某些文章的阅读量这么高?

一个好的文章标题,能吸引读者的目光,能让一篇普通的文章在无数普通的文章中脱颖而出.可以这么说,一篇文章阅读量的多少,很大一部分原因来自标题. 精彩的标题 说明文或议论文,要尽量采用精简.精彩的语言,概括文章的主要内容,作为标题.方法如下: 巧用比喻,让标题"活"起来 适当运用比喻,能生动形象地展现出文章的内容,能吸引读者的目光. **示例** 原标题:民族正在衰亡 修改后:曾经辉煌的民族,现在正如天边的落日--慢慢落下. **鉴赏** 将民族正在衰亡比做天边慢慢落下的落日,让原来&qu

&lt;转&gt;如何调试makefile

makefile 的调试有点像魔法.可惜,并不存在makefile 调试器之类的东西可用来查看特定规则是如何被求值的,或某个变量是如何被扩展的.相反,大部分的调试过程只是在执 行输出的动作以及查看makefile.事实上,GNU make 提供了若干可以协助调试的内置函数以及命令行选项. 用来调试makefile 的一个最好方法就是加入调试挂钩以及使用具保护的编程技术,让你能够在事情出错时恢复原状.我将会介绍若干基本的调试技术以及我所发现的最有用的具保 护能力的编码习惯. 1.make 的调试功

Java编程规范总结

代码总体原则 1.1 Java编程遵循的通用原则: 清晰第一.易于维护.易于重构. 简洁为美.易于理解.易于实现. 选择合适的风格,团队保持一致. 1.2 还需要注意一下方面: 面向对象编程隐藏了很多内部实现细节,使用许多JAVA特性时,要注意正确使用.比如:多线程并发.泛型.装箱数据类型.异常处理.对象克隆等. 2. 代码风格 原则1:命名原则:为包.类.方法.变量取一个好名字,使代码易于理解. 原则2:禁止使用魔鬼数字 不要直接使用数字,应采用有意义的静态变量或枚举来代替. 原则3:常量命名