本篇博客是《软件开发者成长完全攻略》系列翻译文章第 3 章。
原文地址:How To Develop Technical Skills

在上一章中,我已经列出了一张你需要学习的开发技术清单,这张技术清单很长,你可能会好奇应该如何学习这些技术,以及学习完这些要花多长的时间。

既然你提到了时间,那么我告诉你,你将会花跟你当程序员一样长的时间来学习这些技术。你应该将学习视为一段旅程,而非终点。你永远可以变得更好 —— 只要你愿意的话。

之前我在技术学习上用了错误的方法,因此浪费了大量的时间。但是,我在给 Pluralsight 录制超过 50 套在线技术课程的三年里,学会了如何快速学习一门开发技术,同时将它教给别人。

我曾经以为,学习开发技术的最好方法就是抱着一本厚厚的参考手册,然后从头开始一页一页地读它。那时候,我读了很多超过 800 页的大部头,然而我的开发技术并没有在这过程中有很大的进步。倒是我的手臂有可能因为总是携带这么重的书而变得更加强壮。

我不希望你跟我犯同样的错误,或者如果你已经犯了,我会给你展示一种更好的方法。

学习如何快速学习

在我们进入到具体的开发技术学习前,我觉得有必要花时间说一下如何快速学习,以及如何自学。

我会在本节中的后面几章中深入讲解自学的方法,不过现在我想先讲一点比较基础的东西,以及说说我是如何快速学习任何领域的知识的。

就像我说过的,我花了大量的时间学习以及教授不同的技术。我曾经在几星期内学习了几门编程语言,并立马使用这些语言进行授课。在这个过程中,我创造了一种快速学习任何领域知识的可靠系统。

这不是一个有意识的过程,而是我不得不这么做。我试着以如此快的速度学习,以至于我得想出更有效的做事方式,然后很自然地,创造出的的学习系统帮助我学得越来越快。

在这里我只会讲一些基础的东西,因为我有一门关于这个主题的完整课程 “10 Steps to Learn Anything Quickly(快速学习任何领域知识的 10 个步骤)”,同时在我的另一本书 Soft Skills(软技能)中也有几章是关于这个主题的。

基本步骤

其中最基本的思想很简单。本质上来说,你要先了解你想学习的东西是什么,以及它是属于哪个领域的知识。

针对你想学习的主题,你需要掌握充分的信息以理解它的整体思想,并将它缩小到一个足够小的范围,让自己可以在一个切实可行的时间内掌握它。

接着,你需要定一个目标。你要明白自己学习的是什么东西,以及为何你需要学习它,更重要的是,你要有一个标准来证明自己已经掌握了这个知识。太多的人在不了解如何确定自己是否掌握这个知识的情况下就开始学习了。

在有了这些起步知识后,你就可以开始学习这个主题的相关资源了。我推荐不要只是从头到尾一页一页地读书,而是收集不同的资源,包括书籍,博客,播客,杂志,视频课程以及教程,专家观点等。

然后,你要利用这些资料去制订一个真正的学习计划。你可以你收集到的资源制订一个系统的,步骤清晰的计划来学习你想学习的知识。

举例来说,你可以利用一本书中的目录来帮你确定这个主题的学习顺序以及哪部分是最重要的。最基础的思想就是确定你要学习的这个主题中所有知识的学习顺序。

之后,你就可以深入了。从计划开始,学习每个你需要掌握的模块主题。针对每个模块,学习到足够起步的知识,把玩一下它们,然后回过头来解答自己在这过程中发现的任何问题。

本质上来说,你需要做的是在实践中学习,关于这个我们等一下会详细讲解。

这里的关键是不要在一开始就学习太多的知识。相反地,要利用好奇的天性在把玩这个主题的过程中来驱动自己。然后再回头去阅读那些书籍,以及其它关于这个主题的内容,当有了一定的体验,同时在脑袋中带着问题的时候,它们会指引你发掘出这个主题中真正重要的知识。

当我们通常阅读大量资料来学习时会碰到的一个最大问题就是无法确定到底哪部分知识才是最重要的。而如果先尝试把玩下并在过程中提出问题,解决问题,通过这种方式学习的知识会真正地印在脑中。

最后,将你学习到的知识教授给别人。教授的形式以及对象并不重要。只要你愿意,可以把它讲给你的狗或者家里后院的松鼠听,这都没有关系。

真正重要的是你要以同外界交流的方式,重新组织你自己脑袋中的想法。而这个过程就是将学习从知识转化成自己的理解的过程

就是这些。上面所讲的是一个基础步骤,对于所有你想学习的知识都是通用的。如果你想获得更详细的示例,完整的学习手册及对应的视频教程,你可以在这里找到:10 Steps to Learn Anything Quickly

现在,让我们谈谈更具体的开发技术的学习。

在实践中学习

我相信所有人都是在实践过程中学习得最好,但是一旦到了开发技术的领域,这个就是唯一的途径了。你不可能通过简单地阅读书本,或者甚至是观看视频教程来学会开发技术。

也许你会懂得某项技术、某门编程语言或者工具可以完成哪些任务,但是直到你开始真正的自己动手使用它们,或者通过它们来解决问题之前,你所学习到的的技术都只是表面上的。

我在上一章中讲到的所有知识,都是需要在书本之外自己动手才能真正学到的技术。这一点对于编程语言来说可能比较明显,但是你真的可以通过阅读源码控制的语法来掌握它吗?

如果你从来没有犯过将文件合并到错误的分支,签出错误版本的源码这类错误的话,你就没有可能使用版本历史来找到 bug 引入的地方,你就没有可能真正掌握源码控制的使用 —— 你只是觉得你自己掌握了。(如果你对这段中提到的技术都不明白,不要担心。)

但是,你不是承诺在本书后面的章节中教我学这些技术吗?我不是正在通过阅读一本书,希望从书中学习到技术吗?是的,但是关键点在于,你的学习不能止步于此。

你可以阅读我写的这些字,并对我讨论的某个主题有一个粗略的认识,但是之后你需要放下这本书,并真正地动手操作,以此来更积极地在实践过程中掌握你所阅读到的知识(至少是针对我们在这里讨论的开发技术)。

如何在实践中学习

冒着重复某些你可能觉得很明显的信息,我要在这里讲解一下如何真正地做到在实践中学习 —— 你可以将这里所讲的,作为某些你已经知道的信息的回顾提醒。

每次你想尝试及学习一门新技术的时候,要从弄清楚这门技术可能帮助你做什么开始。如果你对这项技术没有迫切的需要,你可能要问下自己是否真的有必要学习这门技术。在现实生活中,我们在学习一些从来不会使用的技术上浪费了大量时间。相信我,我对自己做过这样的事感到愧疚,并且这样做一点也不好玩。

如果你对某些知识有即刻的需求,这样学习起来会更容易 —— 你有一个真实需要学习它们的理由。

我相信如果你在没有真正坐飞机到天上,并从飞机上跳下来的话,在这之前学习过的跳伞知识对你来说就跟没有学习过一样。

但是如果我现在没有迫切的技能需求呢?如果我学习技术只是想通过它来找到工作,并且工作中会用到这项技术?

在这种情况下,你需要制造一个学习这个技术的理由。制订一个目标。

在实践中学习的一个例子

让我们来看一个真实的例子。

如果你想学习关系型数据库,以及如何使用它们。

你可以阅读关于数据库的书籍,并自己动手运行一些 sql 语句 —— 这可能会有些效果。

但是如果你的目标是创建一个数据库,并用它来储存自己拥有的电影呢?

如果你的目标是查询这个数据库,插入、删除电影,更新电影标题,等等呢?

如果你的目标是创建一个简单的应用程序来操作数据库,并完成所有的这些操作呢?

现在你有了目标,并且有了一个在实践中学习的方法。

现在,你有了可以直接动手做的事情。

你会如何着手学习关系型数据库呢?你会直接打开书,或者观看相关视频教程,寻找用来解决你实际问题的具体信息。

接着,你真正动手创建和使用一个数据库,而并非只是做一做练习。你有了一个真正的目标。

思考下在这个动手操作和学习的过程中,你会多学习到多少的信息。而且,这样来学习不也是更有意思吗?

我是如何教授开发技术的

正如我在前面说的,我曾经教授过各式各样不同的技术。

因此,了解我是如何通过教学让自己学习技术变得更简单应该对你有好处。通过这种方法,你可以直接将它们应用到你的自学过程中。

能理解吗?

当我进行开发技术教学的时候,我会给他们一个大的全局观,而非教授一大堆他们不是真正需要懂得,或者完全可能自学得到的知识。我会集中精力教授那些能马上产生价值的知识,而当他们想针对一个主题进行深入学习的时候,我会给学生一些我称为“即刻学习”的学习资料。

当我教授开发技术的时候,有三种主要重要的点:

  • 大方向:你可以使用这个技术做什么?
  • 如何入门。
  • 20% 你需要掌握的最重要的知识。

下面让我对它们进行逐步讲解。

大方向:你可以使用这个技术做什么?

我总是从大方向开始的。

我相信 Google 可以解决你的大部分问题,但是你无法 Google 一个你不知道的东西。因此,我首先会试着教我的学生特定技术的大方向,以及对于它能做什么的一个概述。

这一步是很粗浅的。我不会向他们展示这项技术的方方面面;而是带着他们快速浏览以及概述技术地图上的兴趣点。

举例来说,对于一门编程语言,我可以会讨论这门语言的历史,以及它大多数情况下被用于做什么开发。接着,我会向快速向他们展示这门语言的所有构造,以及语言特性 —— 特别是那些这门语言独有的特性。最后,我会向他们介绍这门语言标准库,并说明这些库可以做什么,以及它们涉及到了哪些方面。

这背后的思想是给你一个全局的鸟瞰图,而不是钻入到细节里面。你总是可以为自己感兴趣的点查询相关资料,并进行深入学习。

在这一步,我想排除不知之不知(unknown unknowns)的问题。我要确保你对自己一无所知的东西建立一个体系,这样当你想学习它们的时间,就知道从何入手了。

我的目标是,你不会说,“哎呀,我并不知道 X 可以完成这个功能,”而是说,“我知道 X 可以完成这个功能。但是我不太确定,不过我稍后会弄清楚的。”

你想像一下,一个准备学习木工的人,却不知道钻孔机及 router 的存在是什么样的情形。

你可以不用知道如何使用这些工具,但是如果你甚至不知道它们的存在,这就会对你的学习产生严重的阻碍。

如何入门

接下来,我会教授学生的是如何入门。

这是学习一项技术最困难的部分 —— 这也是“实践”的先驱 —— 所以我会让这个过程尽量无痛。

我会向学生展示如何下载所有必要的软件,安装它们并创建第一个项目,最后对代码进行编译。一旦克服了这个障碍,他们就可以开始自己动手,并真正开始创造各种东西或者学习它们想学的技术。

如果这个入门门槛太高的话,他们就更容易受挫,他们宁愿选择看书或者观看视频教程,而不愿意真正地动手进行实践。

你可以在学习中利用这个方法,确保自己在学习某项技术的过程中,尽早地把注意力放在让自己入门上,去搜索教你如何入门的具体教程或指南,然后从这里开始起步。

学习 20% 最重要的知识

最后,我会尝试教授学生这门技术中最重要的 20% 的知识,这些知识在 80% 的开发过程中都会使用到。

基本上生活中的所有事情都符合帕雷托原则,即所谓的80/20法则,20%的事物会产生80%的价值。而学习一项技术的关键点就在于找出这项技术中的 20%。

在你学习的这项技术中,80% 的工作中都会使用到的 20% 的知识是什么呢?这时通过实践就比单纯地阅读更容易找到答案。

很多的书籍或者教程都写得像一本参考手册,而不是强调你去学习这项技术中最重要的 20% 的知识。但是如果你真正地使用这门技术进行实践了,你立马就会发觉哪些知识经常被用到,因为如果你不知道这些知识的话,在写代码的过程中就会痛苦万分。

让我们再一次用关联数据库来举例子。

正常来说,如果你学习的是关系型数据库,那么手写 select 语句就可以算是这 20% 领域的知识了。

如果你只是单纯地阅读一本 SQL 的书籍,你可能会觉得 select 跟插入、更新、删除、索引以及其它不同的数据库函数同等重要。但是,如果你直接动手尝试并创建一个数据库并使用它的时候,你会发现大部分时间都跟 select 语句打交道。你会立刻发现自己需要去学习如何连接两张表。

相比于浪费大量的时间去学习关于数据库的所有知识,你会将关注点放在学习如何写 select 语句,表连接,以及其它构成这门技术 20% 的最常用操作。

这就是为何实践如何重要的原因。

了解专家是如何工作的也很有帮助,甚至你可以选择以学徒的身份来协助他们工作。通过观察那些使用你正在学习的这门技术工作的高手,同时了解这门技术最重要的 20%,你可以很快地知道你需要学习的知识。

这对于职业培训尤其有效果。

阅读专家写的文章

我准备向你展示最后一个学习技术的方法。成为一个掌握这门技术的专家所写文章的热衷粉。

当我在学习编程这门手艺的时候,我每天都会花 30 分钟来阅读与我正在学习的技术有关的博客。当我真正想深入掌握 C++ 知识的时候,我如饥似渴地阅读Scott Meyers 的《Effective C++》

很多时候,只是听一听专家对于某个主题的见识,你就可以获得比通过自己学习与收集得来的更深的洞见。

掌握一门编程语言或者学会如何使用一门框架是一方面,而理解它们的语言习惯,并用优雅的方法来使用它们是另一回事。

在学习的过程中,向专家学习它们是如何在实际的项目中使用这些技术的。阅读专家对于某个复杂技术的问题或者论点,能帮助你获得更深的理解。

练习,练习,练习

但愿我已经给你几个关于如何学习开发技术,并进一步发展他们的好建议。

你现在应该很清楚在实践中学习的必要性了 —— 特别是当你学习的是编程技术时。同时,你也应该很清楚,针对想要学习的技术,你需要一个实际的计划和一个清晰的目标。

我想给你提最后一个建议。

练习

学习任何一项技术都需要花时间。为了更好地掌握这项技术,你需要经常练习。不要因为它需要花很长的时间才能达到而沮丧,特别是当你觉得自己没有取得任何进展的时候。

只要你制订了一个可靠的计划,以及一个清晰的目标,并且投入你的时间,技术会自然而然来到你手上的。

你所要做的就是坚持下去,并且相信这个过程

关注

如果你喜欢这篇文章,可以关注我的公众号,随时获取我最新的博客文章。

qrcode_for_gh_6e8bddcdfca3_430.jpg