阅读源码(IV)
往期系列: 《由阅读源码想到》 《由阅读源码想到 | 下篇》 《阅读源码(III)》
Eric S.Raymond的写于2014年的《How to learn hacking》是一篇出色的谈论如何阅读源码的文章。(Eric这里的hacking技术,指的是开源项目里的一种 an effective way to acquire general-purpose programming skills,即获取通用编程技艺的有效方法。)
这篇文字里,Eric创造性地提出了incremental-hacking cycle的概念。在他看来,建立起坚实的技术实力,需要经过这么一个循环过程:
选择一个你感兴趣的开源项目。
如果你不是太了解这个项目,通过阅读文档,去学习如何使用这个项目。
为这个项目增添/修改一个小的feature。
不断在代码库中做搜索,直至找到增添这个小feature的正确位置。
为你的改动,生成一个build,对这个build做测试、调式。并为这个改动撰写文档。
将你的改动作为这个项目的patch,发送给这个项目的维护者。
继续询问自己:我现在理解了整个项目吗?如果不是,返回到第三步,选择另外一个更复杂的feature来重复上述操作。
短短7个步骤,蕴含了开源社区如何滋养技术人的合作方式(之后另写文章阐述),及自我技术修炼的精髓。
在这里,我想展开论述第三条。从技术角度讲,第三条是阅读源码的必要衍生——不仅仅是阅读代码,而是要和代码发生作用与反应。
但对于一个newbie来说,第三条充满了陷阱和不知晓的误导。特别是,当第三条的工作,是由你的上司或者同事指派下来,你往往会因为feature功能过于简单,更加无法领会第三条的精髓。
例如,如果这个项目本身有one click的功能,而你被指派的任务是实现一个double click的功能,估计很多newbie会为此抓狂,并深深地感觉受到了伤害和智商上的侮辱。
但实际情况是什么呢?
这里的重点,其实不是写一个简单的feature, 而是以这个小的feature做引子,去带动你找到能够正确添加这个feature的准确位置。
换言之,这是在训练你对代码的搜寻能力和对代码整体脉络的把握能力。当你能够自如地找寻到每一段代码正确的添加位置时,你也就基本掌握了这个项目的代码架构。
另一方面,“添加一段代码”这句话,其实隐含了很多老兵默认但newbie却不一定知道的东西:
如何证明你的添加是正确的?
这段代码会对整个项目产生哪些影响?
如何证明只会产生你认为的这些影响?
支撑这段代码的test case有哪些?
你撰写的test case能否覆盖、囊括了对项目产生的所有影响?
这些默认的隐藏思考点,对newbie是极其残酷的。老兵们没有义务去做过多的解释,往往就是一句“你要多写啊”,然后不断地给你“reject”,不断地重复“你要认真一点啊”这样粗糙的指导。
而如何认真呢?你从来不知道。其实就是这些默认的规则、规范和细致考虑。这些东西是开源社区的默认规则,你得通过不断地阅读其他人的邮件列表和提交工作,来一步步归纳总结:应该在每个看似简单的改动背后,做足、做踏实哪些相应的辅助工作。
如此,你更加可以理解:为什么不能够只是通过阅读代码,而必须通过“写代码”的方式来理解一个项目。所谓的“牵一发而动全身”,如果没有一个明确的操作目标和实际作用,你很难知道这个小小的位置,会造成那么可观的连锁反应。而添加代码,就如同往河里扔进去一颗石子,能够通过切切实实的作用,让那些隐藏在背后的连锁反应逐一显现,从而让你更深刻地去掌握项目背后的实质和逻辑关系。
这样,你也可以理解为什么需要添加一些功能上无足轻重的代码了。因为,如果你对本身的代码架构不够熟悉,而feature本身的技术细节又极端复杂,你将会陷入到一个double difficulty的处境。你的debug,不仅要解决feature的技术细节,还得考虑在代码构架中所引发的影响,这对一个newbie来说就太过困难了。
总结起来,对于newbie来说,一个很矛盾的困境、但却很少有人愿意为你解释清楚的是:你很可能因为这个feature自身的简陋甚至幼稚而轻视这项“添加feature”的任务。但你的轻视,源自于你将这项任务的“用意”弄错了。
这项任务的主菜,不在于feature的高技术含量,而在于让你去探索、评估、理解“即便是这么简单的一个feature添加,它到底会对这个项目本身产生哪些影响?又该如何去验证、测试这些影响?从而去加深你对项目的理解,提高自身吸收代码的技艺。”
近期回顾
《阅读源码(III)》
《2018年03月写字总结》
《再探羊、猪、狗》
如果你喜欢我的文章或分享,请长按下面的二维码关注我的微信公众号,谢谢!
更多信息交流和观点分享,可加入知识星球:
VIP赞赏专区
阅读源码(IV)的更多相关文章
- 【转】使用 vim + ctags + cscope + taglist 阅读源码
原文网址:http://my.oschina.net/u/554995/blog/59927 最近,准备跟学长一起往 linux kernel 的门里瞧瞧里面的世界,虽然我们知道门就在那,但我们还得找 ...
- Spring源码解析——如何阅读源码(转)
最近没什么实质性的工作,正好有点时间,就想学学别人的代码.也看过一点源码,算是有了点阅读的经验,于是下定决心看下spring这种大型的项目的源码,学学它的设计思想. 手码不易,转载请注明:xingoo ...
- Spring源码解析——如何阅读源码
最近没什么实质性的工作,正好有点时间,就想学学别人的代码.也看过一点源码,算是有了点阅读的经验,于是下定决心看下spring这种大型的项目的源码,学学它的设计思想. 手码不易,转载请注明:xingoo ...
- 阅读源码(III)
往期系列: <由阅读源码想到> <由阅读源码想到 | 下篇> Medium上有一篇文章Why You Don't Deserve That Dream Developer Jo ...
- How Tomcat works — 一、怎样阅读源码
在编程的道路上,通过阅读优秀的代码来提升自己是很好的办法.一直想阅读一些开源项目,可是没有合适的机会开始.最近做项目的时候用到了shiro,需要做集群的session共享,经过查找发现tomcat的s ...
- 使用 vim + ctags + cscope + taglist 阅读源码
转自:http://my.oschina.net/u/554995/blog/59927 最近,准备跟学长一起往 linux kernel 的门里瞧瞧里面的世界,虽然我们知道门就在那,但我们还得找到合 ...
- 转载~Linux 平台下阅读源码的工具
Linux 平台下阅读源码的工具 前言 看源代码是一个程序员必须经历的事情,也是可以提升能力的一个捷径.个人认为: 要完全掌握一个软件的方法只有阅读源码在Windows下有sourceinsight这 ...
- Linux 平台下阅读源码的工具链
原文:http://blog.jobbole.com/101322/ 前言 看源代码是一个程序员必须经历的事情,也是可以提升能力的一个捷径.个人认为: 要完全掌握一个软件的方法只有阅读源码. 在Win ...
- Zookeeper_阅读源码第一步_在 IDE 里启动 zkServer(集群版)
上篇文章Zookeeper_阅读源码第一步_在 IDE 里启动 zkServer(单机版)讲了在 idea 里以单机的方式启动zookeeper,这篇介绍一下以集群的方式启动. 集群方式启动,才会真正 ...
随机推荐
- windows下实现win32俄罗斯方块练手,编程的几点心得
编程珠玑2阅读笔记: 1.使用c语言性能监视器,完成对代码的调优工作 2.关联数组: 拓扑排序算法,可以用于当存在遮挡的时候决定三维场景的绘制顺序. 3.小型算法中的测试与调试工具 脚手架程序:&l ...
- Cocos2D添加精灵纹理滤镜实现图像复古效果的转换
大熊猫猪·侯佩原创或翻译作品.欢迎转载,转载请注明出处. 如果觉得写的不好请多提意见,如果觉得不错请多多支持点赞.谢谢! hopy ;) 大家知道Cocos2d本身是一个非常强悍的2d游戏引擎,其中自 ...
- Socket实现聊天客户端
今天在极客学院上看到了一个关于Socket的视频讲解,感觉还不错,就写了份代码,拿来分享一下. Socket使用方法 关于Socket的使用,我们首先要弄清楚的是,在服务器端还是在客户端使用.因为这的 ...
- 《java入门第一季》之HashSet存储自定义对象问题以及注意事项
上一篇http://blog.csdn.net/qq_32059827/article/details/51578158 写到存储字符串类型的时候出现了无序,而且这个无序不是随机那种无序,它是有一定存 ...
- JSP标签JSTL(2)--流程控制
对于流程控制,单纯的用jsp脚本,显得很是繁琐,尤其是遇到if判断的时候,写代码的时候就需要特别的小心,因为极有可能会出现符号不匹配的状况.但是利用标签语言就会大大的改善这一状况. 流程控制 if标签 ...
- Uva - 230 - Borrowers
AC代码: #include <iostream> #include <cstdio> #include <cstdlib> #include <cctype ...
- html倒计时代码
<SPAN id=span_dt_dt></SPAN> <SCRIPT language=javascript> <!-- //document.write( ...
- Linux C 下的大文件操作
这里说的大文件指大小超过4G的文件. 在32位环境下,linux默认打开.读.写超过4G的文件会返回错误.定义如下宏可以突破这个限制,对read/write和fread/fwrite同时有效. 注意它 ...
- Linux IPC实践(8) --共享内存/内存映射
概述 共享内存区是最快的IPC形式.一旦这样的内存映射到共享它的进程的地址空间,这些进程间数据传递不再涉及到内核,换句话说是进程不再通过执行进入内核的系统调用来传递彼此的数据(如图). 共享内存 VS ...
- [leetcode]经典算法题- String to Integer (atoi)
题目描述: 把字符串转化为整数值 原文描述: Implement atoi to convert a string to an integer. Hint: Carefully consider al ...