0%

转自:https://www.pureweber.com/article/recursive-power-4/
递归的力量(四):递归效率
前几天我们在讨论递归的过程中发现,递归在解决某些问题的时候使得我们思考的方式得以简化,代码也更加精炼,容易阅读。那么既然递归有这么多的优点,我们是不是什么问题都要用递归来解决呢?难道递归就没有缺点吗?今天我们就来讨论一下递归的不足之处。
我们知道,递归调用实际上是函数自己在调用自己,而函数的调用开销是很大的,系统要为每次函数调用分配存储空间,并将调用点压栈予以记录。而在函数调用结束后,还要释放空间,弹栈恢复断点。所以说,函数调用不仅浪费空间,还浪费时间。
这样,我们发现,同一个问题,如果递归解决方案的复杂度不明显优于其它解决方案的话,那么使用递归是不划算的。因为它的很多时间浪费在对函数调用的处理上。在C++中引入了内联函的概念,其实就是为了避免简单函数内部语句的执行时间小于函数调用的时间而造成效率降低的情况出现。在这里也是一个道理,如果过多的时间用于了函数调用的处理,那么效率显然高不起来。

阅读全文 »

故事概要:

1967年8月23日,前苏联的联盟一号宇宙飞船在返回大气层时,突然发生了恶性事故--减速速降落伞无法打开。前苏联中央领导研究后决定:向全国实况转播这次事故。当电视台的播音员用沉重的语调宣布,宇宙飞船两个小时后将坠毁,观众将目睹宇航员弗拉迪米·科马洛夫殉难的消息后,举国上下顿时被震撼了,人们沉浸在巨大的悲痛之中。
在电视台上,观众看到了宇航员科马洛夫镇定自若的形象,他面带微笑地对母亲说:"妈妈,您的图像我在这里看得清清楚楚,包括您的头上的每根白发,您能看清我吗?""能,能看清楚。儿啊,妈妈一切都很好,你放心吧!"这时,科马洛夫的女儿也出现在电视屏幕上,她只有12岁。科马少夫说:"女儿,你不要哭。""我不哭……"女儿已泣不成声,但她强忍悲痛说:"爸爸,您是苏联英雄,我想告诉您,英雄的女儿会像英雄那样生活的!"科马洛夫叮嘱女儿说:"学习时,要认真对待每一个小数点。联盟一号今天发生的一切,就是因为地面检查时忽略了一个小数点……"
时间一分一秒地过去,距离宇宙飞船坠毁只有7分钟了,科马洛夫向全国的电视观众挥挥手说:"同胞们,请允许我在这茫茫的太空中与你们告别。"
这是一次惊心动魄的告别仪式。科马洛夫永远地走了,他留下了对亲人对祖国永恒的爱。但更震撼人心的是他对女儿说的那番话。它警示着人们:对待人生不能有丝毫的马虎,否则,即使是一个细枝末节,也会让你付出深重的甚至是永远无法弥补的代价.

阅读全文 »

浮点运算中避免使用等量判断的原则。
具体的理由见下文。
http://www.dengshenyu.com/%E8%AE%A1%E7%AE%97%E6%9C%BA%E7%A7%91%E5%AD%A6/2016/04/11/float-number.html
通常的做法,写一个Equals()函数,两个相减,如果值小于给定的精度值,就返回相等。

处理摄入误差的问题。
使用BigDecimal进行精确运算
http://www.cnblogs.com/chenssy/archive/2012/09/09/2677279.html

重建系统的有道理的一篇文章。

下次老板让你重构系统,让他看看这篇文章

上个月,有个以前的同事问我:“你在的时候,为什么不把原来的系统都重做了,我们明明有实力啊”。

我说:“我们也做了很多事情嘛,系统稳定性、安全性、增加冗余、理清各模块职责、API通讯机制的建立、内部分层的整理。”

他说:“对,但我还是想知道,你为什么不把系统重做了呢?”

于是我问:“我离职之后,后来似乎多投了不少人重做系统?结果怎么样呢?”

阅读全文 »

事情的起因是, 1970年,赞比亚修女 Mary Jucunda 给 Ernst Stuhlinger 博士写了一封信,他因在火星之旅工程中的原创性研究,成为 NASA(美国航空航天局)Marshall 太空航行中心的科学副总监。信中,Mary Jucunda 修女问道:目前地球上还有这么多小孩子吃不上饭,他怎么能舍得为远在火星的项目花费数十亿美元。
Stuhlinger 很快给Jucunda 修女回了信,同时还附带了一张题为“升起的地球”的照片,这张标志性的照片是宇航员 William Anders 于1968年在月球轨道上拍摄的(照片中可以看到月球的地面)。他这封真挚的回信随后由 NASA 以《为什么要探索宇宙》为标题发表。

阅读全文 »

重建还是重构? 作者 Ben Linders ,译者 覃璐 发布于 2015年12月3日
在 Agile Testing Days 2015大会上, Wouter Lagerweij谈到了如何重建一个遗留系统而不是重构它,来帮助团队采取敏捷实践,比如测试驱动开发,自动化测试,持续交付。他的谈话基于他的博客文章 Don’t Refactor. Rebuild. Kinda。

InfoQ采访了 Lagerweij关于是什么让重构如此困难,重建软件的风险是否比重构小,以及持续交付如何配合软件的重建。InfoQ同时请教了他关于重建和重构的建议。

InfoQ:您能解释一下是什么使得重构这么困难吗?

Lagerweij:只要你去做,重构是一项相当简单的实践。同样的例子是单元测试。只要你坚持为代码编写测试用例,或者清理代码中的设计问题,一小步一小步的,这并不困难。

阅读全文 »

Compile、Make和Build的区别

针对Java的开发工具,一般都有Compile、Make和Build三个菜单项,完成的功能的都差不多,但是又有区别。

编译,是将源代码转换为可执行代码的过程。编译需要指定源文件和编译输出的文件路径(输出目录)。Java的编译会将java编译为class文件,将非java的文件(一般成为资源文件、比如图片、xml、txt、poperties等文件)原封不动的复制到编译输出目录,并保持源文件夹的目录层次关系。

在Java的集成开发环境中,比如Eclipse、IDEA中,有常常有三种与编译相关的选项Compile、Make、Build三个选项。这三个选项最基本的功能都是完成编译过程。但又有很大的区别,区别如下:
1、Compile:只编译选定的目标,不管之前是否已经编译过。

2、Make:编译选定的目标,但是Make只编译上次编译变化过的文件,减少重复劳动,节省时间。(具体怎么检查未变化,这个就不用考虑了,IDE自己内部会搞定这些的)

3、Build:是对整个工程进行彻底的重新编译,而不管是否已经编译过。Build过程往往会生成发布包,这个具体要看对IDE的配置了,Build在实际中应用很少,因为开发时候基本上不用,发布生产时候一般都用ANT等工具来发布。Build因为要全部编译,还要执行打包等额外工作,因此时间较长。