`

JAVA语言学校的危险性(译文)

 
阅读更多

转自:http://www.kingofcoders.com/viewNews.php?type=news&id=977&number=6227553960025427169282446503048670435732834387093022266826221089132606890328137539756348070289192463

原文:http://www.joelonsoftware.com/articles/ThePerilsofJavaSchools.html

JAVA语言学校的危险性(译文)

作者:Joel Spolsky

译者:阮一峰

原文: http://www.joelonsoftware.com/articles/ThePerilsofJavaSchools.html

发表日期 2005年12月29日,星期四

如今的孩子变懒了。

多吃一点苦,又会怎么样呢?

我一定是变老了,才会这样喋喋不休地抱怨和感叹“如今的孩子”。为什么他们不再愿意、或者说不再能够做艰苦的工作呢。

当我还是孩子的时候,学习编程需要用到穿孔卡片(punched cards)。那时可没有任何类似“退格”键(Backspace key)这样的现代化功能,如果你出错了,就没有办法更正,只好扔掉出错的卡片,从头再来。

回想1991年,我开始面试程序员的时候。我一般会出一些编程题,允许用任何编程语言解题。在99%的情况下,面试者选择C语言。

如今,面试者一般会选择Java语言。

说到这里,不要误会我的意思。Java语言本身作为一种开发工具,并没有什么错。

等一等,我要做个更正。我只是在本篇特定的文章中,不会提到Java语言作为一种开发工具,有什么不好的地方。事实上,它有许许多多不好的地方,不过这些只有另找时间来谈了。

我在这篇文章中,真正想要说的是,总的来看,Java不是一种非常难的编程语言,无法用来区分优秀程序员和普通程序员。它可能很适合用来完成工作,但是这个不是今天的主题。我甚至想说,Java语言不够难,其实是它的特色,不能算缺点。但是不管怎样,它就是有这个问题。

如果我听上去像是妄下论断,那么我想说一点我自己的微不足道的经历。大学计算机系的课程里,传统上有两个知识点,许多人从来都没有真正搞懂过的,那就是指针(pointers)和递归(recursion)。

你进大学后,一开始总要上一门“数据结构”课(data structure), 然后会有线性链表(linked list)、哈希表(hash table),以及其他诸如此类的课程。这些课会大量使用“指针”。它们经常起到一种优胜劣汰的作用。因为这些课程非常难,那些学不会的人,就表明他们的 能力不足以达到计算机科学学士学位的要求,只能选择放弃这个专业。这是一件好事,因为如果你连指针很觉得很难,那么等学到后面,要你证明不动点定理 (fixed point theory)的时候,你该怎么办呢?

有些孩子读高中的时候,就能用BASIC语言在Apple II型个人电脑上,写出漂亮的乒乓球游戏。等他们进了大学,都会去选修计算机科学101课程,那门课讲的就是数据结构。当他们接触到指针那些玩意以后,就 一下子完全傻眼了,后面的事情你都可以想像,他们就去改学政治学,因为看上去法学院是一个更好的出路[1]。关于计算机系的淘汰率,我见过各式各样的数 字,通常在40%到70%之间。校方一般会觉得,学生拿不到学位很可惜,我则视其为必要的筛选,淘汰那些没有兴趣编程或者没有能力编程的人。

对于许多计算机系的青年学生来说,另一门有难度的课程是有关函数式编程(functional programming)的课程,其中就包括递归程序设计(recursive programming)。MIT将这些课程的标准提得很高,还专门设立了一门必修课(课程代号6.001[2]),它的教材(Structure and Interpretation of Computer Programs,作者为Harold Abelson和Gerald Jay Sussman Abelson,MIT出版社1996年版)被几十所、甚至几百所著名高校的计算系机采用,充当事实上的计算机科学导论课程。(你能在网上找到这本教材的 旧版本,应该读一下。)

这些课程难得惊人。在第一堂课,你就要学完Scheme语言[3]的几乎所有内容,你还会遇到一个不动点函数(fixed-point function),它的自变量本身就是另一个函数。我读的这门导论课,是宾夕法尼亚大学的CSE 121课程,真是读得苦不堪言。我注意到很多学生,也许是大部分的学生,都无法完成这门课。课程的内容实在太难了。我给教授写了一封长长的声泪俱下的 Email,控诉这门课不是给人学的。宾夕法尼亚大学里一定有人听到了我的呼声(或者听到了其他抱怨者的呼声),因为如今这门课讲授的计算机语言是 Java。

我现在觉得,他们还不如没有听见呢。

这就是争议所在。许多年来,像当年的我一样懒惰的计算机系本科生不停地抱怨,再加上计算机业界也在抱怨毕业生不够用,这一切终于造成了重大恶果。过 去十年中,大量本来堪称完美的好学校,都百分之百转向了Java语言的怀抱。这真是好得没话说了,那些用“grep”命令[4]过滤简历的企业招聘主管, 大概会很喜欢这样。最妙不可言的是,Java语言中没有什么太难的地方,不会真的淘汰什么人,你搞不懂指针或者递归也没关系。所以,计算系的淘汰率就降低 了,学生人数上升了,经费预算变大了,可谓皆大欢喜。

学习Java语言的孩子是幸运的,因为当他们用到以指针为基础的哈希表时,他们永远也不会遇到古怪的“段错误”[5](segfault)。他们永 远不会因为无法将数据塞进有限的内存空间,而急得发疯。他们也永远不用苦苦思索,为什么在一个纯函数的程序中,一个变量的值一会保持不变,一会又变个不 停!多么自相矛盾啊!

他们不需要怎么动脑筋,就可以在专业上得到4.0的绩点。

我是不是有点太苛刻了?就像电视里的“四个约克郡男人”[6](Four Yorkshiremen)那样,成了老古板?就在这里吹嘘我是多么刻苦,完成了所有那些高难度的课程?

我再告诉你一件事。1900年的时候,拉丁语和希腊语都是大学里的必修课,原因不是因为它们有什么特别的作用,而是因为它们有点被看成是受过高等教 育的人士的标志。在某种程度上,我的观点同拉丁语支持者的观点没有不同(下面的四点理由都是如此):“(拉丁语)训练你的思维,锻炼你的记忆。分析拉丁语 的句法结构,是思考能力的最佳练习,是真正对智力的挑战,能够很好地培养逻辑能力。”以上出自Scott Barker之口(http://www.promotelatin.org/whylatin.htm)。但是,今天我找不到一所大学,还把拉丁语作为必修课。指针和递归不正像计算机科学中的拉丁语和希腊语吗?

说到这里,我坦率地承认,当今的软件代码中90%都不需要使用指针。事实上,如果在正式产品中使用指针,这将是十分危险的。好的,这一点没有异议。与此同时,函数式编程在实际开发中用到的也不多。这一点我也同意。

但是,对于某些最激动人心的编程任务来说,指针仍然是非常重要的。比如说,如果不用指针,你根本没办法开发Linux的内核。如果你不是真正地理解了指针,你连一行Linux的代码也看不懂,说实话,任何操作系统的代码你都看不懂。

如果你不懂函数式编程,你就无法创造出MapReduce[7],正是这种算法使得Google的可扩展性(scalable)达到如此巨大的规 模。单词“Map”(映射)和“Reduce”(化简)分别来自Lisp语言和函数式编程。回想起来,在类似6.001这样的编程课程中,都有提到纯粹的 函数式编程没有副作用,因此可以直接用于并行计算(parallelizable)。任何人只要还记得这些内容,那么MapRuduce对他来说就是显而 易见的。发明MapReduce的公司是Google,而不是微软,这个简单的事实说出了原因,为什么微软至今还在追赶,还在试图提供最基本的搜索服务, 而Google已经转向了下一个阶段,开发世界上最大的并行式超级计算机——Skynet[8]的H次方的H次方的H次方的H次方的H次方的H次方。我觉 得,微软并没有完全明白,在这一波竞争中它落后多远。

除了上面那些直接就能想到的重要性,指针和递归的真正价值,在于那种你在学习它们的过程中,所得到的思维深度,以及你因为害怕在这些课程中被淘汰, 所产生的心理抗压能力,它们都是在建造大型系统的过程中必不可少的。指针和递归要求一定水平的推理能力、抽象思考能力,以及最重要的,在若干个不同的抽象 层次上,同时审视同一个问题的能力。因此,是否真正理解指针和递归,与是否是一个优秀程序员直接相关。

如果计算机系的课程都与Java语言有关,那么对于那些在智力上无法应付复杂概念的学生,就没有东西可以真的淘汰他们。作为一个雇主,我发现那些 100%Java教学的计算机系,已经培养出了相当一大批毕业生,这些学生只能勉强完成难度日益降低的课程作业,只会用Java语言编写简单的记账程序, 如果你让他们编写一个更难的东西,他们就束手无策了。他们的智力不足以成为程序员。这些学生永远也通不过MIT的6.001课程,或者耶鲁大学的CS 323课程。坦率地说,为什么在一个雇主的心目中,MIT或者耶鲁大学计算机系的学位的份量,要重于杜克大学,这就是原因之一。因为杜克大学最近已经全部 转为用Java语言教学。宾夕法尼亚大学的情况也很类似,当初CSE 121课程中的Scheme语言和ML语言,几乎将我和我的同学折磨至死,如今已经全部被Java语言替代。我的意思不是说,我不想雇佣来自杜克大学或者 宾夕法尼亚大学的聪明学生,我真的愿意雇佣他们,只是对于我来说,确定他们是否真的聪明,如今变得难多了。以前,我能够分辨出谁是聪明学生,因为他们可以 在一分钟内看懂一个递归算法,或者可以迅速在计算机上实现一个线性链表操作函数,所用的时间同黑板上写一遍差不多。但是对于Java语言学校的毕业生,看 着他们面对上述问题苦苦思索、做不出来的样子,我分辨不出这到底是因为学校里没教,还是因为他们不具备编写优秀软件作品的素质。Paul Graham将这一类程序员称为“Blub程序员”[9](www.paulgraham.com/avg.html)。

Java语言学校无法淘汰那些永远也成不了优秀程序员的学生,这已经是很糟糕的事情了。但是,学校可以无可厚非地辩解,这不是校方的错。整个软件行业,或者说至少是其中那些使用grep命令过滤简历的招聘经理,确实是在一直叫嚷,要求学校使用Java语言教学。

但是,即使如此,Java语言学校的教学也还是失败的,因为学校没有成功训练好学生的头脑,没有使他们变得足够熟练、敏捷、灵活,能够做出高质量的 软件设计(我不是指面向对象式的“设计”,那种编程只不过是要求你花上无数个小时,重写你的代码,使它们能够满足面向对象编程的等级制继承式结构,或者说 要求你思考到底对象之间是“has-a”从属关系,还是“is-a”继承关系,这种“伪问题”将你搞得烦躁不安)。你需要的是那种能够在多个抽象层次上, 同时思考问题的训练。这种思考能力正是设计出优秀软件架构所必需的。

你也许想知道,在教学中,面向对象编程(object-oriented programming,缩写OOP)是否是指针和递归的优质替代品,是不是也能起到淘汰作用。简单的回答是:“不”。我在这里不讨论OOP的优点,我只 指出OOP不够难,无法淘汰平庸的程序员。大多数时候,OOP教学的主要内容就是记住一堆专有名词,比如“封装”(encapsulation)和“继承 ”(inheritance)”,然后再做一堆多选题小测验,考你是不是明白“多态”(polymorphism)和“重载”(overloading) 的区别。这同历史课上,要求你记住重要的日期和人名,难度差不多。OOP不构成对智力的太大挑战,吓不跑一年级新生。据说,如果你没学好OOP,你的程序 依然可以运行,只是维护起来有点难。但是如果你没学好指针,你的程序就会输出一行段错误信息,而且你对什么地方出错了毫无想法,然后你只好停下来,深吸一 口气,真正开始努力在两个不同的抽象层次上,同时思考你的程序是如何运行的。

顺便说一句,我有充分理由在这里说,那些使用grep命令过滤简历的招聘经理真是荒谬可笑。我从来没有见过哪个能用Scheme语言、 Haskell语言和C语言中的指针编程的人,竟然不能在二天里面学会Java语言,并且写出的Java程序,质量竟然不能胜过那些有5年Java编程经 验的人士。不过,人力资源部里那些平庸的懒汉,是无法指望他们听进去这些话的。

再说,计算机系承担的发扬光大计算机科学的使命该怎么办呢?计算机系毕竟不是职业学校啊!训练学生如何在这个行业里工作,不应该是计算机系的任务。 这应该是社区高校和政府就业培训计划的任务,那些地方会教给你工作技能。计算机系给予学生的,理应是他们日后生活所需要的基础知识,而不是为学生第一周上 班做准备。对不对?

还有,计算机科学是由证明(递归)、算法(递归)、语言(λ演算[10])、操作系统(指针)、编译器(λ演算)所组成的。所以,这就是说那些不教 C语言、不教Scheme语言、只教Java语言的学校,实际上根本不是在教授计算机科学。虽然对于真实世界来说,有些概念可能毫无用处,比如函数的科里 化(function currying)[11],但是这些知识显然是进入计算机科学研究生院的前提。我不明白,计算机系课程设置委员会中的教授为什么会同意,将课程的难度下 降到如此低的地步,以至于他们既无法培养出合格的程序员,甚至也无法培养出合格的能够得到哲学博士PhD学位[12]、进而能够申请教职、与他们竞争工作 岗位的研究生。噢,且慢,我说错了。也许我明白原因了。

实际上,如果你回顾和研究学术界在“Java大迁移”(Great Java Shift)中的争论,你会注意到,最大的议题是Java语言是否还不够简单,不适合作为一种教学语言。

我的老天啊,我心里说,他们还在设法让课程变得更简单。为什么不用匙子,干脆把所有东西一勺勺都喂到学生嘴里呢?让我们再请助教帮他们接管考试,这 样一来就没有学生会改学“美国研究”[13](American studies)了。如果课程被精心设计,使得所有内容都比原有内容更容易,那么怎么可能期望任何人从这个地方学到任何东西呢?看上去似乎有一个工作小组 (Java task force)正在开展工作,创造出一个简化的Java的子集,以便在课堂上教学[14]。这些人的目标是生成一个简化的文档,小心地不让学生纤弱的思想, 接触到任何EJB/J2EE的脏东西[15]。这样一来,学生的小脑袋就不会因为遇到有点难度的课程,而感到烦恼了,除非那门课里只要求做一些空前简单的 计算机习题。

计算机系如此积极地降低课程难度,有一个理由可以得到最多的赞同,那就是节省出更多的时间,教授真正的属于计算机科学的概念。但是,前提是不能花费 整整两节课,向学生讲解诸如Java语言中int和Integer有何区别[16]。好的,如果真是这样,课程6.001就是你的完美选择。你可以先讲 Scheme语言,这种教学语言简单到聪明学生大约只用10分钟,就能全部学会。然后,你将这个学期剩下的时间,都用来讲解不动点。

唉。

说了半天,我还是在说要学1和0。

(你学到了1?真幸运啊!我们那时所有人学到的都是0。)

================

注解:

[1] 在美国,法学院的入学者都必须具有本科学位。通常来说,主修政治学的学生升入法学院的机会最大。

[2] 在麻省理工学院,计算机系的课程代码都是以6开头的,6.001表明这是计算机系的最基础课程。

[3] Scheme语言是LISP语言的一个变种,诞生于1975年的MIT,以其对函数式编程的支持而闻名。这种语言在商业领域的应用很少,但是在计算机教育领域内有着广泛影响。

[4] grep是Unix/Linux环境中用于搜索或者过滤内容的命令。这里指的是,某些招聘人员仅仅根据一些关键词来过滤简历,比如本文中的Java。

[5] 段错误(segfault)是segmentation fault的缩写,指的是软件中的一类特定的错误,通常发生在程序试图读取不允许读取的内存地址、或者以非法方式读取内存的时候。

[6] 《四个约克郡男人》(Four Yorkshiremen),是英国电视系列喜剧At Last the 1948 Show中的一部,与上个世纪70年代问世。内容是四个约克郡男人竞相吹嘘,各自的童年是多么困苦,由于内容太夸张,所以显得非常可笑。

[7] MapReduce是一种由Google引入使用的软件框架,用于支持计算机集群环境下,海量数据(PB级别)的并行计算。

[8] Skynet是美国系列电影《终结者》(Terminator)中一个控制一切、与人类为敌的超级计算机系统的名称,通常将其看作虚构的人工智能的代表。

[9] Blub程序员(Blub programmers)指的是那些企图用一种语言,解决所有问题的程序员。Blub是Paul Graham假设的一种高级编程语言。

[10] λ演算(lambda calculus)是一套用于研究函数定义、函数应用和递归的形式系统,在递归理论和函数式编程中有着广泛的应用。

[11] 函数的科里化(function currying)指的是一种多元函数的消元技巧,将其变为一系列只有一元的链式函数。它最早是由美国数学家哈斯格尔·科里(Haskell Curry)提出的,因此而得名。

[12] 在美国,所有基础理论的学科,一律授予的都是哲学博士学位(Doctor of Philosophy),计算机科学系亦是如此。

[13] 美国研究(American studies)是对美国社会的经济、历史、文化等各个方面进行研究的一门学科。这里指的是,计算机系学生不会因为课程太难被淘汰,所以就不用改学相对容易的“美国研究”。

[14] 参见http://www.sigcse.org/topics/javataskforce/java-task-force.pdf。

[15] J2EE是Java2平台企业版(Java 2 Platform,Enterprise Edition),指的是一整套企业级开发架构。EJB(Enterprise JavaBean)属于J2EE的一部分,是一个基于组件的企业级开发规范。它们通常被认为是Java中相对较难的部分。

[16] 在Java语言中,int是一种数据类型,表示整数,而Integer是一个适用于面向对象编程的类,表示整数对象。两者的涵义和性质都不一样。

(完)

**************************

*原文:*

**************************

Joel on Software

The Perils of JavaSchools

by Joel Spolsky
Thursday, December 29, 2005

Lazy kids.

Whatever happened to hard work?

A sure sign of my descent into senility is bitchin' and moanin' about "kids these days," and how they won't or can't do anything hard any more.

“You were lucky. We lived for three months in a brown paper bag in a septic tank. We had to get up at six in the morning, clean the bag, eat a crust of stale bread, go to work down the mill, fourteen hours a day, week-in week-out, and when we got home our Dad would thrash us to sleep with his belt.” — Monty Python's Flying Circus,Four Yorkshiremen

When I was a kid, I learned to program on punched cards. If you made a mistake, you didn't have any of these modern features like a backspace key to correct it. You threw away the card and started over.

When I started interviewing programmers in 1991, I would generally let them use any language they wanted to solve the coding problems I gave them. 99% of the time, they chose C.

Nowadays, they tend to choose Java.

Now, don't get me wrong: there's nothing wrong with Java as an implementation language.

Wait a minute, I want to modify that statement. I'm not claiming, in this particular article, that there's anything wrong with Java as an implementation language. There are lots of things wrong with it but those will have to wait for a different article.

Instead what I'd like to claim is that Java is not, generally, a hard enough programming language that it can be used to discriminate between great programmers and mediocre programmers. It may be a fine language to work in, but that's not today's topic. I would even go so far as to say that the fact that Java is not hard enough is a feature, not a bug, but it does have this one problem.

If I may be so brash, it has been my humble experience that there are two things traditionally taught in universities as a part of a computer science curriculum which many people just never really fully comprehend: pointers and recursion.

You used to start out in college with a course in data structures, with linked lists and hash tables and whatnot, with extensive use of pointers. Those courses were often used as weedout courses: they were so hard that anyone that couldn't handle the mental challenge of a CS degree would give up, which was a good thing, because if you thought pointers are hard, wait until you try to prove things about fixed point theory.

All the kids who did great in high school writing pong games in BASIC for their Apple II would get to college, take CompSci 101, a data structures course, and when they hit the pointers business their brains would just totally explode, and the next thing you knew, they were majoring in Political Science because law school seemed like a better idea. I've seen all kinds of figures for drop-out rates in CS and they're usually between 40% and 70%. The universities tend to see this as a waste; I think it's just a necessary culling of the people who aren't going to be happy or successful in programming careers.

The other hard course for many young CS students was the course where you learned functional programming, including recursive programming. MIT set the bar very high for these courses, creating a required course (6.001) and a textbook (Abelson & Sussman's Structure and Interpretation of Computer Programs) which were used at dozens or even hundreds of top CS schools as the de facto introduction to computer science. (You can, and should, watch an older version of the lectures online.)

The difficulty of these courses is astonishing. In the first lecture you've learned pretty much all of Scheme, and you're already being introduced to a fixed-point function that takes another function as its input. When I struggled through such a course, CSE121 at Penn, I watched as many if not most of the students just didn't make it. The material was too hard. I wrote a long sob email to the professor saying It Just Wasn't Fair. Somebody at Penn must have listened to me (or one of the other complainers), because that course is now taught in Java.

I wish they hadn't listened.

Think you have what it takes? Test Yourself Here!

Therein lies the debate. Years of whinging by lazy CS undergrads like me, combined with complaints from industry about how few CS majors are graduating from American universities, have taken a toll, and in the last decade a large number of otherwise perfectly good schools have gone 100% Java. It's hip, the recruiters who use "grep" to evaluate resumes seem to like it, and, best of all, there's nothing hard enough about Java to really weed out the programmers without the part of the brain that does pointers or recursion, so the drop-out rates are lower, and the computer science departments have more students, and bigger budgets, and all is well.

The lucky kids of JavaSchools are never going to get weird segfaults trying to implement pointer-based hash tables. They're never going to go stark, raving mad trying to pack things into bits. They'll never have to get their head around how, in a purely functional program, the value of a variable never changes, and yet, it changes all the time! A paradox!

They don't need that part of the brain to get a 4.0 in major.

Am I just one of those old-fashioned curmudgeons, like the Four Yorkshiremen, bragging about how tough I was to survive all that hard stuff?

Heck, in 1900, Latin and Greek were required subjects in college, not because they served any purpose, but because they were sort of considered an obvious requirement for educated people. In some sense my argument is no different that the argument made by the pro-Latin people (all four of them). "[Latin] trains your mind. Trains your memory. Unraveling a Latin sentence is an excellent exercise in thought, a real intellectual puzzle, and a good introduction to logical thinking," writes Scott Barker. But I can't find a single university that requires Latin any more. Are pointers and recursion the Latin and Greek of Computer Science?

Now, I freely admit that programming with pointers is not needed in 90% of the code written today, and in fact, it's downright dangerous in production code. OK. That's fine. And functional programming is just not used much in practice. Agreed.

But it's still important for some of the most exciting programming jobs. Without pointers, for example, you'd never be able to work on the Linux kernel. You can't understand a line of code in Linux, or, indeed, any operating system, without really understanding pointers.

Without understanding functional programming, you can't invent MapReduce, the algorithm that makes Google so massively scalable. The terms Map and Reduce come from Lisp and functional programming. MapReduce is, in retrospect, obvious to anyone who remembers from their 6.001-equivalent programming class that purely functional programs have no side effects and are thus trivially parallelizable. The very fact that Google invented MapReduce, and Microsoft didn't, says something about why Microsoft is still playing catch up trying to get basic search features to work, while Google has moved on to the next problem: building Skynet^H^H^H^H^H^H the world's largest massively parallel supercomputer. I don't think Microsoft completely understands just how far behind they are on that wave.

But beyond the prima-facie importance of pointers and recursion, their real value is that building big systems requires the kind of mental flexibility you get from learning about them, and the mental aptitude you need to avoid being weeded out of the courses in which they are taught. Pointers and recursion require a certain ability to reason, to think in abstractions, and, most importantly, to view a problem at several levels of abstraction simultaneously. And thus, the ability to understand pointers and recursion is directly correlated with the ability to be a great programmer.

Nothing about an all-Java CS degree really weeds out the students who lack the mental agility to deal with these concepts. As an employer, I've seen that the 100% Java schools have started churning out quite a few CS graduates who are simply not smart enough to work as programmers on anything more sophisticated than Yet Another Java Accounting Application, although they did manage to squeak through the newly-dumbed-down coursework. These students would never survive 6.001 at MIT, or CS 323 at Yale, and frankly, that is one reason why, as an employer, a CS degree from MIT or Yale carries more weight than a CS degree from Duke, which recently went All-Java, or U. Penn, which replaced Scheme and ML with Java in trying to teach the class that nearly killed me and my friends, CSE121. Not that I don't want to hire smart kids from Duke and Penn -- I do -- it's just a lot harder for me to figure out who they are. I used to be able to tell the smart kids because they could rip through a recursive algorithm in seconds, or implement linked-list manipulation functions using pointers as fast as they could write on the whiteboard. But with a JavaSchool Grad, I can't tell if they're struggling with these problems because they are undereducated or if they're struggling with these problems because they don't actually have that special part of the brain that they're going to need to do great programming work. Paul Graham calls them Blub Programmers.

It's bad enough that JavaSchools fail to weed out the kids who are never going to be great programmers, which the schools could justifiably say is not their problem. Industry, or, at least, the recruiters-who-use-grep, are surely clamoring for Java to be taught.

But JavaSchools also fail to train the brains of kids to be adept, agile, and flexible enough to do good software design (and I don't mean OO "design", where you spend countless hours rewriting your code to rejiggle your object hierarchy, or you fret about faux "problems" like has-a vs. is-a). You need training to think of things at multiple levels of abstraction simultaneously, and that kind of thinking is exactly what you need to design great software architecture.

You may be wondering if teaching object oriented programming (OOP) is a good weed-out substitute for pointers and recursion. The quick answer: no. Without debating OOP on the merits, it is just not hard enough to weed out mediocre programmers. OOP in school consists mostly of memorizing a bunch of vocabulary terms like "encapsulation" and "inheritance" and taking multiple-choice quizzicles on the difference between polymorphism and overloading. Not much harder than memorizing famous dates and names in a history class, OOP poses inadequate mental challenges to scare away first-year students. When you struggle with an OOP problem, your program still works, it's just sort of hard to maintain. Allegedly. But when you struggle with pointers, your program produces the line Segmentation Fault and you have no idea what's going on, until you stop and take a deep breath and really try to force your mind to work at two different levels of abstraction simultaneously.

The recruiters-who-use-grep, by the way, are ridiculed here, and for good reason. I have never met anyone who can do Scheme, Haskell, and C pointers who can't pick up Java in two days, and create better Java code than people with five years of experience in Java, but try explaining that to the average HR drone.

But what about the CS mission of CS departments? They're not vocational schools! It shouldn't be their job to train people to work in industry. That's for community colleges and government retraining programs for displaced workers, they will tell you. They're supposed to be giving students the fundamental tools to live their lives, not preparing them for their first weeks on the job. Right?

Card Punch -- yes, I learned Fortran on one of these when I was 12.Still. CS is proofs (recursion), algorithms (recursion), languages (lambda calculus), operating systems (pointers), compilers (lambda calculus) -- and so the bottom line is that a JavaSchool that won't teach C and won't teach Scheme is not really teaching computer science, either. As useless as the concept of function currying may be to the real world, it's obviously a prereq for CS grad school. I can't understand why the professors on the curriculum committees at CS schools have allowed their programs to be dumbed down to the point where not only can't they produce working programmers, they can't even produce CS grad students who might get PhDs and compete for their jobs. Oh wait. Never mind. Maybe I do understand.

Actually if you go back and research the discussion that took place in academia during the Great Java Shift, you'll notice that the biggest concern was whether Java was simple enough to use as a teaching language.

My God, I thought, they'retrying to dumb down the curriculum even further! Why not spoon feed everything to the students? Let's have the TAs take their tests for them, too, then nobody will switch to American Studies. How is anyone supposed to learn anything if the curriculum has been carefully designed to make everything easier than it already is? There seems to be a task force underway (PDF) to figure out a simple subset of Java that can be taught to students, producing simplified documentation that carefully hides all that EJB/J2EE crap from their tender minds, so they don't have to worry their little heads with any classes that you don't need to do the ever-easier CS problem sets.

The most sympathetic interpretation of why CS departments are so enthusiastic to dumb down their classes is that it leaves them more time to teach actual CS concepts, if they don't need to spend two whole lectures unconfusing students about the difference between, say, a Javaint and an Integer. Well, if that's the case, 6.001 has the perfect answer for you: Scheme, a teaching language so simple that the entire language can be taught to bright students in about ten minutes; then you can spend the rest of the semester on fixed points.

Feh.

I'm going back to ones and zeros.

(You had ones? Lucky bastard! All we got were zeros.)

Are you a Junior in college who can rip through a recursive algorithm in seconds, or implement linked-list manipulation functions using pointers as fast as you can write on the whiteboard? Check out our summer internships in New York City! Applications are due February 1st.


Work with me, here! Fog Creek Software has great paid internships in software development for qualified college students. They’re in New York City. Free housing, lunch, and more. And you get to work on real, shipping software with the smartest developers in the business.

Want to know more?

You’re reading Joel on Software, stuffed with years and years of completely raving mad articles about software development, managing software teams, designing user interfaces, running successful software companies, and rubber duckies.



About the author.

I’m Joel Spolsky, founder of Fog Creek Software, a New York company that proves that you can treat programmers well and still be highly profitable. Programmers get private offices, free lunch, and work 40 hours a week. Customers only pay for software if they’re delighted. We make FogBugz, an enlightened project management system designed to help great teams develop brilliant software, and Fog Creek Copilot, which makes remote desktop access easy.

© 2000-2009 Joel Spolsky
<script language="Javascript" type="text/javascript"> <!-- document.write('<a href="mai'); document.write('lto'); document.write(':&#106;&#111;&#101;&#108;'); document.write('@'); document.write('&#106;&#111;&#101;&#108;&#111;&#110;&#115;&#111;&#102;&#116;&#119;&#97;&#114;&#101;&#46;&#99;&#111;&#109;">'); document.write('&#106;&#111;&#101;&#108;'); document.write('@'); document.write('&#106;&#111;&#101;&#108;&#111;&#110;&#115;&#111;&#102;&#116;&#119;&#97;&#114;&#101;&#46;&#99;&#111;&#109;<//a>'); // --> </script>joel@joelonsoftware.com

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics