计算机科学基础班(第三期)报名

计算机科学基础班(第二期)已经成功结束两个月了。每次的教学都让我发现以前没有注意到的细节,以至于每一次都在改进。现在休息了两个月之后,我觉得大概可以召集第三期的报名工作了。

第二期课程总结

第二期课程调低了学费,增加了课程规模。虽然减轻了学生的经济负担,让更多的人能够参加,总体的效果也很好,但这使得我和助教的工作都比较辛苦。

我的教学跟普通学校有很大的不同,不仅在于内容,讲课方式,还在于精心设计的练习。练习是教学中很重要的部分,学生自身能力的提高,其实主要是由循序渐进的练习来完成的。就像设计良好的健身练习一样,它们会逐渐让学生的头脑变得强壮,而不是让他们半途放弃或者受伤。

每一个练习都是单独提交,而不是全部练习做完了才一次性提交。这样学生会得到准确而及时的反馈,避免重复犯错误。对于思路不清而卡住的练习,也会收到量身定制的准确提示,让思维走上正路,却不“剧透”最终结果。这样的设计,使得学生的思维得到最大限度的锻炼,逐渐获得独立思考的能力。

对于学生的练习,我的要求不仅是要正确,而且要简单,逻辑思路清晰,就算标点符号和排版都要符合最高的标准。几乎没有任何大学会纠正和引导学生这方面的风格,而这其实是很重要的。

我们为每一个学生都建立了一个“辅导群”,里面有四个人:学生,老师和两个助教。这样的设计使得学生能最大限度的得到反馈。即使老师在忙其他事,助教有时间也可以回复。助教不清楚的地方,都由老师亲自来看。

相比大学里的情况,教授和助教是只有上课时或者 office hours 才见得到的。作业都是一次性提交批改,不可能来来回回的提示和指引。这种特别的教学方式,使得对时间的利用效率大大提高。课后的每个练习本身也都变成了教学,所以虽然只有 8 节课,“实际教学时间”的量却是大大高于讲课时间的。这样的练习是如此有趣,以至于到后面几节课时,学生们都希望我少讲,少“剧透”,从而可以把更多的知识点作为练习给他们自己思考。这样的教学方式和效果是我的生涯中前所未见的,可能是世界上独一无二的。虽然是集体班,但其实每个人都得到了近似于一对一的教学。

虽然效果很好,这同时也增加了老师和助教的工作。第二期课程中的许多天,我和助教们直到晚上 12 点都还在回复学生的练习,给他们提示和指点。由于很多学生平时要工作,所以直到周末才开始做练习,以至于周末的时候涌来大量的练习信息。我有两个非常认真热心的助教,有时候看到他们深夜和周末还在忙着回复学生,我都叫他们快去休息。助教的反映是,虽然微信聊天都设置为了“免打扰”,学生也知道晚上不期待我们回复,但看到学生提交的练习,总是忍不住会去看,去回复。我可以说,在当今的世界,可能很少有人会这么在乎教学这个事了。

第三期课程报名

因为第二期的学费和学生数量,使得教学进行比较累,所以第三期课程不会再采用第二期的学费价格和班级大小。第三期课程的具体计划如下:

  1. 学费调整回原先的 12000 人民币,可以接受相应的美元付款。
  2. 班级大小限制为 15 人以内。
  3. 讲课课时仍然是 8 节课,每节课大概 2 小时。但因为我发现其中有一两节课内容很少,时间其实没有很好利用,所以也可能把其中的一两节课换成练习发布。
  4. 因为讨论会效果不是很明显,而且可能占用学生的工作时间,不再设置每星期一次的讨论会。
  5. 课程会在春节之后,班级容量达到之后开始。

报名方式

报名请发送 email 到 yinwang.advising@icloud.com。标题为《计算机科学基础班(第三期)报名》。来信请说明自己的基本信息,附件发送一个简历。由于班级人数有限,而且为了课程的顺利,会对申请人进行选择。像申请国外大学一样,请写一段“personal statement”说明自己的学习动机。因为你的态度决定了是否录取,所以对于申请请慎重,不要着急和轻率。如果觉得合适,我会通知你进行下一步的面试。

课程大纲

根据第二期课程的经验,我想对课程的内容做一个比以前详细的说明。之前一直对课程内容没有很多说明,一方面为的是留下自由发挥的空间,一方面是为了让学生有一定的神秘感,引发好奇心。但这么简单的说明似乎会让不知情的人误以为“已经学过这些东西”,而其实几乎没有任何人可以说这句话。有时候会发现一些人看了说明之后,自以为我教的内容他都会了,我只为他们感到可惜。

下面简要说一下课程的内容:

课程使用 JavaScript,会是一个非常重视“动手”的课程,但其实内容不依赖于任何编程语言特有的特性。学生从零开始,学会计算机科学最核心的思想,从无到有创造出高级编程语言里出现的几乎所有特性。

课程的设计是一个缓慢增加难度,不轻松,却很安全的山路,它通往很高的顶峰。要参加课程,请做好付出努力的准备,在两个月的时间里,你每天需要至少一个小时来做练习,有的练习可能需要好几个小时才能做对。跟其他计算机教学不同,学生不会因为缺少基础而放弃,不会误入歧途,也不会掉进陷阱出不来。学生需要付出很多的时间和努力,但没有努力是白费的。

第一课:跟一般课程不同,我不从所谓“Hello World”程序开始,也不会叫学生做一些好像有趣而其实无聊的小游戏。一开头我就讲最核心的内容:函数。关于函数只有很少几个知识点,但它们却是一切的核心。我设计了很多精巧的练习。教学的关键在于让学生在只知道很少的知识点的时候,对它们进行反复的练习,以至于头脑可以灵活自如地对函数进行很高级的思考。

第一课的练习每个都很小,只需要一两行代码,但很有趣。练习逐渐加大难度,直至超过大学博士班的水平,有的达到世界级的难度。我把所有的术语都改头换面,要求学生不上网搜索相关内容,为的是他们的思维不受任何已有信息的干扰,独立做出这些练习。这里面的逻辑却是井井有条,一环扣一环。很有趣的是,好些学生居然把最难的练习都做出来了,完全零基础的学生都能做出绝大部分,这是我在世界一流大学的学生里都没看到过的。具体的内容因为不剧透的原因,我就不继续说了。

第二课:数值递归。第二课学生就接触到计算机科学(或数学)最重要的内容:递归。从最简单的递归函数开始,引导他们理解递归的本质,掌握对递归进行系统化思考的思路,也为学习后来的数据结构做好铺垫。

第三课:链表。从无到有,学生会从零开始,制造出自己的数据结构来。第一个数据结构就是链表,学生会在练习中实现许多操作链表的函数。这些函数是精心挑选出来的,在将来也会很有用。很多这些函数是函数式编程语言的函数库里存在的,但通过自己的努力把它们写出来,学生会掌握关键的递归思路,使他们能够在将来自如地对这类数据结构进行思考。

跟一般的编程课里讲的数据结构不同,我们实现的数据结构都是所谓「函数式数据结构」,它们具有一些我们在后面的课程需要的重要性质,而且因为它们结构清晰,逻辑简单,比起普通的数据结构书籍,会更容易理解,思路更加清晰。

第四课:树结构。从链表,逐渐推广出更复杂一些的数据结构——树。

第五课:计算器。在熟悉了树的基本操作之后,学生会利用树的思路,实现一个比较高级的计算器,它可以计算任意嵌套的算术表达式。

第六课:查找结构。理解程序里如何实现 key-value 查找结构,并且亲手实现两种重要的查找数据结构。这些查找结构也都是函数式数据结构。

第七课:解释器。利用之前练习中打好的基础,学生会亲手实现计算机科学中最重要,也是通常认为最难的概念——解释器。解释器是理解计算机学科中很多工程理念的关键,比如操作系统,数据库,网络系统。对解释器的深入理解,也能帮助你理解很多其它学科,比如人类语言。

第八课:类型检查器。在解释器的基础上,学生会理解并实现一个相当高级的类型检查器,使得他们掌握的知识接近于实现出像 Java 这样的静态类型语言。学生会理解类型系统的原理,理解其中的规则。类型系统的实现,一般只会在博士级别的研究中才会出现,而我的学生从零开始都可以掌握这门深奥的技术。

虽然解释器和类型系统看似就是是课程的顶峰,其实途中我会通过“奖励练习”的方式补充其它内容。比如第二期的课程途中,我临时设计了一个 parser 的练习,做完了所有其它练习的同学通过这个练习,理解了 parser 的本质原理,写出了一个简单但是逻辑非常严密的 parser。“奖励练习”之所以叫“奖励”,原因是并不是所有学生都能得到这个练习,只有那些付出了努力,在其他练习中做到融会贯通,学有余力的学生才会给这个练习。为了避免其他学生耗费太多时间做额外的练习,误入歧途,这些练习并不给基础的部分都还比较薄弱的同学。

如果理解了以上内容是什么,你可能就不会再来问“我可不可以参加高级班”了,因为极少有人真的理解了以上的内容,就算世界上最高级职位的一些程序员,大学里的教授,对于他们也有很多含糊不清的地方。所以一个朋友看了我的内容说,你这不叫“基础班”,只能叫“大师班”。我希望这个基础班能帮助人们获得明亮的眼睛,能帮助他们看明白,破解很多其它内容。所以呢,“高级班”可能在很长时间之内都不需要了。