Erlang编程实践中绝大多数时候是在和List打交道:取头元素,遍历,匹配...为什么Erlang和其它函数式编程的语言都对对List情有独钟呢?《Erlang and OTP in Action》一书的附录B中提到了这个问题,其背后的思想就是引用透明(Referential transparency).

  下面这段文字摘录自维基百科:

    Referential transparency and referential opaqueness are properties of parts of computer programs. An expression is said to be referentially transparent if it can be replaced with itsvalue without changing the behavior of a program (in other words, yielding a program that has the same effects and output on the same input). The opposite term is referentially opaque.  [定义]

While in mathematics all function applications are referentially transparent, in programming this is not always the case. The importance of referential transparency is that it allows theprogrammer and the compiler to reason about program behavior. This can help in proving correctness, simplifying an algorithm, assisting in modifying code without breaking it, oroptimizing code by means of memoization, common subexpression elimination or parallelization. [好处]

    Referential transparency is one of the principles of functional programming; only referentially transparent functions can be memoized (transformed into equivalent functions which cache results). Some programming languages provide means to guarantee referential transparency. Some functional programming languages enforce referential transparency for all functions.[与函数式编程的关系]

   As referential transparency requires the same results for a given set of inputs at any point in time, a referentially transparent expression is therefore deterministic by definition.

 http://en.wikipedia.org/wiki/Referential_transparency_(computer_science)

   解读一下上面的文字,先说定义:如果一个表达式能够被它的值代替,它就是引用透明的;换句话说:一段程序对于相同的输入都有相同的输出,它就是引用透明的;<<Erlang and OTP in Action>>里面给的定义更具体一些:给定一个变量X以及变量X的值,那么X的值就不会再变化;显然Erlang的单次赋值(single-assignment)保障了引用透明.引用透明的好处?这个书中提到了三点(1)减少出错 (2)容易并行化 (3)更容易做内存管理喝多线程因为对于已经存在的数据都不再具有写权限 第三点可以比较一下.net的垃圾回收和Erlang的垃圾回收,Erlang是不会出现旧数据持有新数据引用的情况的.维基百科中列举的好处更多一些,可以继续点击做延伸阅读.

   上文也提到了引用透明是函数式编程的原则之一,所有这些又和List有什么关系呢?我们看一个例子:

   现在有一个List  L=[1,2,3,4,5,6,7,8,9] 要做到引用透明我们只能在L头部添加元素,而不能是尾部,因为如果可以这样做,别的L引用持有者就会发现莫名其妙多了一个元素.而在头部添加数据能够保持原有List的不被破坏掉.这样做效率也很高,复杂度O(1).

下面直接抄书了:

     Getting back to lists, this referential transparency guarantee means that if you already have a list (maybe you got it as an argument to a function), you can’t add elements to the end of that list, because if you did, then anybody who had a reference to it would discover that an extra last element had materialized from nowhere. That’s not allowed in Erlang.
     But adding to the left (using list cells) is no problem, because the original list is never disturbed—you create a new cell that points to the first cell of the original list, saying “I’m like that list over there, but with this new element added to the head.”

     Hence, list cells are an elegant solution to the problem of growing lists dynamically in a referentially transparent system; and the implementation is so simple that cells work very efficiently indeed. Many extremely clever people have tried (for decades) to come up with a solution that would allow both adding to the end and lower memory usage while preserving the transparency property, but those solutions have tended to be both very complicated to implement and less efficient in the general case.

   在应用层面,单一赋值已经保证了引用透明,上面解释已经是在底层实现的角度去做的分析了,暂时止步于此了.

 

 

This is why you may have heard Erlang is said to suck at string manipulation: there is no built-in string type like in most other languages. This is because of Erlang's origins as a language created and used by telecom companies. They never (or rarely) used strings and as such, never felt like adding them officially. However, most of Erlang's lack of sense in string manipulations is getting fixed with time: The VM now natively supports Unicode strings, and overall gets faster on string manipulations all the time.

 

There is also a way to store strings as a binary data structure, making them really light and faster to work with. All in all, there are still some functions missing from the standard library and while string processing is definitely doable in Erlang, there are somewhat better languages for tasks that need lots of it, like Perl or Python.