我为什么讨厌Perl
shhgs 2006-01-08 04:15:40 我为什么讨厌Perl
如果你是一个不懂Perl的人,如果你想知道是不是应该学Perl,
那么这篇文档就是给你准备的。不管你最后的决定是什么,
花时间读读这篇文档肯定是值得的。判断要由你来给,
我这里给出的只是事实。
1. scalar, list
Perl号称按照人类语言设计。英语里有单数和复数之分,
因此Perl设置了两种变量,scalar和list。
应该说,这并不坏,但问题出在
$a = @list
不管Perler们怎样解释,这种语法肯定是错的。
当我们赋值的时候,我们隐含地就认定两者相等了。
也就是说,执行完$a = @list之后,$a应该就是@list。
而相等又意味着自反和传递。也就是说如果a==b,那么
b==a;同时如果 a==b,b==c,那么a==c。
赋值就意味着相等,相等就意味着自反和传递,
这两个规则Perl也是承认的,
但是,当我们考察$a=@list的时候,它崩溃了。
当$a=@list之后,$a==@list吗?@list == $a吗?
如果$a = @list; $b = @list2; $a == $b; 请问@list == @list2吗?
对这种为贪图少敲两个键而乱用运算符造成逻辑上的矛盾,
我几乎是本能地产生反感的。虽然要不是为了写这篇帖子,
我未必能总结出上面那番道理。但是作为一个程序员,或者说作为一个想做程序员的人,
你虽然可以不知道它错在哪里,但是你必须能意识到它错了。
2. list, hash, scalar 和 一致性
或许我们应该抱着实用主义的态度接受$a = @list,告诉自己$a = @list的时候,
实际上是在去@list的长度。但非常遗憾,Perl有它自己的逻辑,
一种正常人无法理解的逻辑。
Perl的hash和list是可以任意转换的。这也无可厚非。但是
%hash = (
US => Washington,
China=> Beijing,
British => London,
France => Paris,
Russia => Moscow
);
@list = %hash;
print ($a = @list);
print "\n";
print ($a = %hash);
print "\n";
如果说我可以自欺欺人地认为$a = @list是在取@list的长度,
那么现在我已经不知道该怎么骗自己了。
3. 上下文
Perl引入了上下文的概念。如果这不能算是不负责任的话,至少也是大胆地过了头。
上下文是一个很主观的概念,同样一句话,你理解的上下文和我理解的上下文就可能不一样。
如果是人在交谈,那我们可以停下来,问一下,
但程序又怎么能停下来。
所以,如果程序员的理解错了(天晓得到底是谁对谁错),那这个bug就太难找了。
$a = 1;
print $a +1;
谁都知道,这里我们期望的是程序打印出2,但实际上,
Perl会认为$a是一个filehandler。
这里只是因为有了print,$a才被理解为fliehandler,
在其他很多地方(我不敢说任何地方,我不知道有没有人敢说这两个字),
$a +1都表示给$a加一个1。
类似这种陷阱,Perl肯定还有很多。但是你无法事先预知,只有碰到了才知道,
或者说碰到了也不知道,只有排错排出来之后才知道。
于是你该知道,万一碰上一个这种错误,会有多麻烦了吧。
4. 普适性的缺失
人在学习的时候并不是仅仅靠记忆,更多的是依靠逻辑推理。
比如上例,$a = @list是在取@list的长度,
而@list = %hash是把%hash的键和值放到@list里面,
所以正常人的反应是,$a = %hash应该是取%hash里面有几对键值,
或者%hash里面总共放了多少个键和值。但Perl给的却是一个莫名其妙的3/8。
我不知道这个东西表示什么意思,我也不知道它是怎么来的。
我只知道它是在故意侮辱我的智商。
不知道Perler又会给什么解释,但我知道,这种解释必定是我无法接受的。
我的推理没有错,所以如果他们能推理出相反的结论,那么他们必定错了。
而错了还这么振振有辞,还这么理直气壮,我无言 。。。
Perl的语法的混乱是非常明显的,你只要稍微留心一下就能发现很多。
这是由它的哲学决定的,是它发展的必然产物,所以我估计随着时间的推移,
这种地方会越来越多。西谚有云"Philosophy matters",此诚至理名言,果不我欺也。
5. 虚伪的自由
Perl号称是一种自由的语言,是一种可以用多种方式写同一条语句的语言。
很多人也真是看中这一点才去学的Perl。但是作为一个理性的人,
你应该有自己的主见,你应该知道什么才是真正的自由。
自由,首先是一种权利,是一种按照自己的思路,理解问题、解决问题的权利。
其次,自由是一种表达的自由,是一种无拘无束将自己的观点传播出去的自由。
遗憾的是,这两条Perl都不能满足。
Perl有它的思路,比如$a = @list,$a = %hash,
比如print $a +1。要理解它,你必须抛弃自己的思路,必须接受Perl的逻辑。
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
对一个真正酷爱自由的人来说,这是一件无比痛苦,无比屈辱的事。
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
再看第二条,表达的自由。程序员的思想就是程序,就是算法加数据结构。
而这两者和语言是没有关系的。就像苏格拉底和庄子都是伟大的哲学家,
但他们的哲学思想同他们用哪种语言来写书是没有关系的一样。
但如果他们要把他们的思想传播出去,就不得不借助语言。
因此,如果编程语言的表达能力不强,再好的算法也实现不了。
从这个意义上说,汇编比机器语言自由,C比汇编自由,Java比C自由,
而Python比Java自由。
再来看Perl,它在这个方面,做得并不出色,甚至很差。
Perl不是一种表达能力很强的语言。它带了很浓的shell痕迹。
比如函数的参数、返回值,文件测试,以及那些莫名其妙的符号。
至于OO和reference,更是古怪和滑稽。因此,写Perl代码的时候,
我不得不把很大一部分精力放在语言的细节上,
这跟Python“思路到,代码出”的感觉相比,差得实在太远了。
写尚且如此痛苦,何况是读。Perl的代码是出了名的乱,再加上
"there's more than one way to do it"的motto,真是看了就让人头大。
有时我甚至会想,如果把Perl代码里的空格全部去掉,
是不是会被人认为是base64编码的文本。
最后我想用两个比喻来形容Perl和Python所定义的自由。
在一个叫Perl的小镇,有一条法律。任何人都可以在任何地方涂鸦。
墙上,马路上,桌子上,甚至别人的衣服上。但是它涂鸦的内容只能是
“Larry万岁!”
在一个叫Python的小镇,也有一条法律。居民只能到市政厅的公告栏上帖帖子,
帖子必须用A1白纸,必须用Courier 20号字体打印。但是帖子的内容不限,
你甚至可以写,“Guido下台!”
什么是自由?你自己看。
6. 态度决定一切
Perl有如此之多的问题,但这还不是最糟的,更糟的是Perler的态度。
看看Perl是如何为它的复杂性辩解的。
---- http://www.perl.com/pub/a/2003/06/25/perl6essentials.html ----
The Waterbed Theory of Complexity
The natural tendency in human languages is to keep overall
complexity about equivalent, both from one language to the next,
and over time as a language changes. Like a waterbed,
if you push down the complexity in one part of the language,
it increases complexity elsewhere. A language with a rich system of
sounds (phonology) might compensate with a simpler syntax.
A language with a limited sound system might have a complex way of
building words from smaller pieces (morphology). No language is
complex in every way, as that would be unusable. Likewise,
no language is completely simple, as too few distinctions
would render it useless.
---- http://www.perl.com/pub/a/2003/06/25/perl6essentials.html ----
这是彻头彻尾的狡辩。Perl只是在模仿人类语言,而且是一种很初级的模仿,
它根本上还是一种编程语言。编程语言根本就不存在所谓的waterbed theory。
汇编在各个方面都比机器语言简单,C比汇编简单,。。。,因此Perl也可以,
而且完全应该做得简单一些。
我从来没有见过比这更无耻的狡辩。抱有这种心态,哪怕Perl到了60版,
还会是一样的糟糕。