锁定老帖子 主题:如何避免产生赋值语句
精华帖 (0) :: 良好帖 (12) :: 新手帖 (2) :: 隐藏帖 (1)
|
|
---|---|
作者 | 正文 |
发表时间:2010-08-03
我在之前的文章里谈论过赋值语句的危害性。 使用赋值语句会使程序变的冗长,更难理解。但事实上,赋值语句对编程来说是一种基本语句,想限制它的使用几乎是不可能的。幸运的是,我们实际上是能做到的,下面我就会向你展示如何去做。
用正确的方式初始化
“正确”方式的主要优点是你能很方便的浏览 “错误”方式之所以存在完全是因为很多老式的编程语言都强制要求在程序的开始处先声明变量。这样编译器好处理。但现在这已经不是问题了,即使在C语言里。 构造新数据
这样做很重要。它能保证变量被定义后不会被改变。不留任何机会。 人们使用“错误”方式一般有两个原因:高效和简洁。效率并不是个问题,现代编译器能够通过给变量重新分配地址来优化性能。而由于简洁而导致的语义模糊是得不偿失的。 用函数,不要用过程
“正确”方式使用的是一个普通的数字函数:它接受输入值,返回计算后的值。另一边,“错误”方式使用了过程 。跟函数不一样,过程不仅会影响返回的结果,还能影响其它数据,例如,过程中可以修改它的参数值。这会使这些参数很容易被污染。 所以,当能够使用函数的时候,尽量不要使用过程。你的程序这样会变得更简单。这种技巧可以让你避免去思考如何去做 (变换一个字符串),而是如何被做 (一个变换了的字符串)。要着眼于最终结果,而不是处理过程。 “错误”方式之所以存在完全是由于许多老的编程语言很难处理复杂的返回值。你只能返回单个数字。所以,当需要一个内容更丰富的返回值时,你只能在过 程中达到这个目的。而真正的返回值通常是一些简单的错误标号代码。然而现在不同了,返回复杂的结果已经不再是个问题。即使是在C语言里你也可以返回复杂的 结果。 固化你的对象在很多的入门级的介绍面向对象编程的课程中,你能看到这样一个著名的二维坐标的例子:
这样设计的原因很简单:你可以通过构造函数创建一个新的坐标,然后通过 然而,从代码本身看,却是没必要的复杂化了,而且有几个主要的错误:
正确的设计更简单,而且不失功能:
另外,如果你愿意,你可以把 使用纯功能性数据结构从上面的介绍里我们说明了应该构建新数据 。这个建议即使是大数据结构也是有效的。意外吗,它并不是像你想象的那样失去作用。有时候你为了避免每次都拷贝整个数据结构,你可能要使用修改操作。而数组和hash table就是属于这种情况的。 这种情况下你应该是使用我们所谓的纯功能性数据结构。如果你想对这有所了解,Chris Okasaki’s thesis (也是同名著作)是个好的教材。这里,我只给大家简单的讲讲linked list。 一个链接表要么是个空表,要么是其中有个单元格存着一个指向另一个表的指针。
这样的数据结构如果在ML语言里是很好设计出来的,但在以类为基础的语言里会稍微有点复杂:
你可以看到,现在这个List类是不可变的。我们不能修改
此时,在l的顶部加入
或者,在代码里:
当我们不能这样做时有时,你不能避免赋值操作,或者受其它因素限制。也许是你需要更高的效率,你必须修改数据状态来优化程序。或者由于一些外界因素影响,比如一个用户。或者由于你使用的语言不能自动处理内存使用,这些都会阻止你使用纯功能性的数据结构 。 这种情况下你所能做的最好的方式是隔离那些程序中不合规范的代码(那些使用赋值语句的代码)。比如说,你想给一个数组排序,你必须用quicksort。Quicksort严重的依赖于变换转移操作,但是你可以隐藏这些操作:
于是,当 相反的,当你与其它业务有交互时,要小心的将交互部分的代码和运算部分的代码分隔开。比如你要写段在屏幕上画个点的程序,而且能根据鼠标的移动而移动。写出来可能会是这样:
这里有个错误,它在主程序里对越界坐标进行了检查。更好的方式是这样:
现在,主程序变得更简单了。运算部分,
不管你怎么写, 结论我说的这些都是关于降低耦合的技巧。每个程序都应该有很清晰的内部边界。每个模块应暴露最少量的接口。这能使程序更易于理解和使用。避免使用赋值语句,坚持对象恒定的原则能使接口清晰明确。但这也不是银弹,这只是辅助手段。很有用的辅助手段。
译文来源:外刊IT评论
:)
声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |
发表时间:2010-08-03
翻译的不错,希望这种译文能多一些。
|
|
返回顶楼 | |
发表时间:2010-08-03
按照你的说法,一个变量一旦定义,就不需要再修改,如果需要同样的变量,那么就重新定义一个。我可以这么理解吗? |
|
返回顶楼 | |
发表时间:2010-08-03
我怎么觉得这框框条条,一概而论的文章很傻?
|
|
返回顶楼 | |
发表时间:2010-08-03
函数式编程的价值观,语言的副作用会导致错误的发生,所以小心的避开状态,和OO完全相反的思路。对大数据量做处理时,性能和易用的分布式,是其超级亮点。花一些时间,熟悉一下思路,编程水平的确就会提高很多。
|
|
返回顶楼 | |
发表时间:2010-08-03
总结起来,在java里,就是全部用final关键词。
|
|
返回顶楼 | |
发表时间:2010-08-03
我有点疑问,既然变量不让它变了,还叫变量吗
|
|
返回顶楼 | |
发表时间:2010-08-03
曾经有一段时间我们公司的checkstyle开了变量要求final这条规则,巨烦人。
|
|
返回顶楼 | |
发表时间:2010-08-03
Crusader 写道 我怎么觉得这框框条条,一概而论的文章很傻?
+1 你可以说推荐如何如何去做 直接说这种做法那种做法错误,非常非常错误,偏偏写出的理由又只能说明该做法不太好 |
|
返回顶楼 | |
发表时间:2010-08-03
jslfl 写道 我有点疑问,既然变量不让它变了,还叫变量吗
那就叫常量。 其实都是炒的冷饭了,函数式编程里面早就这样了,完全的函数式编程不允许使用变量的,半截的函数式编程也是不推荐使用变量。 用习惯了就很舒服了,不用害怕多线程问题,一个 名称 x,可以漫天放,反正他永远只会是那一个值。 |
|
返回顶楼 | |