V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐学习书目
Learn Python the Hard Way
Python Sites
PyPI - Python Package Index
http://diveintopython.org/toc/index.html
Pocoo
值得关注的项目
PyPy
Celery
Jinja2
Read the Docs
gevent
pyenv
virtualenv
Stackless Python
Beautiful Soup
结巴中文分词
Green Unicorn
Sentry
Shovel
Pyflakes
pytest
Python 编程
pep8 Checker
Styles
PEP 8
Google Python Style Guide
Code Style from The Hitchhiker's Guide
lynn0977
V2EX  ›  Python

怎么阅读学习源代码

  •  1
     
  •   lynn0977 · 2020-02-09 23:18:33 +08:00 · 7925 次点击
    这是一个创建于 1749 天前的主题,其中的信息可能已经有所发展或是发生改变。
    想通过阅读一些开源项目,提高自己的知识水平,怎样学比较高效,希望大家分享一下自己的方法和经验。
    28 条回复    2020-05-16 10:00:52 +08:00
    suotm
        1
    suotm  
       2020-02-10 00:09:39 +08:00   ❤️ 1
    刚好在看一篇博客,推荐你去看一下,关键词是:
    Become a Better Developer by Reading Source Code Steve Gordon
    secondwtq
        2
    secondwtq  
       2020-02-10 00:23:02 +08:00   ❤️ 3
    你问对时候了,新鲜出炉的: http://www.yinwang.org/blog-cn/2020/02/05/how-to-read-code
    webshe11
        3
    webshe11  
       2020-02-10 00:23:43 +08:00
    恰好我最近也看到一篇博客: https://www.yinwang.org/blog-cn/2020/02/05/how-to-read-code (水深火热)
    webshe11
        4
    webshe11  
       2020-02-10 00:24:14 +08:00
    @secondwtq 哇 我们几乎同时发的
    wanguorui123
        5
    wanguorui123  
       2020-02-10 00:25:13 +08:00 via iPhone
    单步调试
    AX5N
        6
    AX5N  
       2020-02-10 02:32:19 +08:00   ❤️ 1
    王垠这个不适合普通人(菜鸟)看,普通人看别人源代码主要是为了提高见识,对自己的知识盲区查缺补漏。
    AX5N
        7
    AX5N  
       2020-02-10 02:32:54 +08:00
    比如网银说
    ```
    很多人误以为看大型项目可以提升自己,而没有看到大型项目不过是几十行核心代码的扩展,很多部分是低水平重复。几十行平庸甚至晦涩的代码,重复一万次,就成了几十万行。看那些低水平重复的部分,是得不到什么提升的。
    ```
    AX5N
        8
    AX5N  
       2020-02-10 02:33:48 +08:00
    比如王垠说

    很多人误以为看大型项目可以提升自己,而没有看到大型项目不过是几十行核心代码的扩展,很多部分是低水平重复。几十行平庸甚至晦涩的代码,重复一万次,就成了几十万行。看那些低水平重复的部分,是得不到什么提升的。

    普通人都不知道什么叫做低水平重复,什么叫做垃圾代码,不去看看怎么知道呢。
    IRuNamu
        9
    IRuNamu  
       2020-02-10 02:39:36 +08:00 via Android
    話說 c++單步調試下指針亂跳根本看不過來的清況下 有什么好方法看源碼
    OldPanda
        10
    OldPanda  
       2020-02-10 07:27:36 +08:00   ❤️ 1
    刻意的看开源代码只会让自己痛苦,花费大量时间精力而不知所得,我一般会带着几分好奇和几分兴趣,比如说自己写的某个小项目用到了,或者突然对某一块知识感到很有兴趣,找到优秀开源代码的片段,详细推敲别人是如何实现的,为什么这样实现,感觉这样比“别人都说这个项目好,那我也来看看”从而阅读源码的效果好得多
    jie170601
        11
    jie170601  
       2020-02-10 07:29:44 +08:00 via Android
    同求好方法,断点调试可以搞清楚某些细节的具体实现,但难把握整体,又没有文档,怎么看比较好
    tianshilei1992
        12
    tianshilei1992  
       2020-02-10 08:03:44 +08:00 via iPhone
    王垠有一点说的我很赞同,就是得先知道这个代码是做什么的,再去看具体的代码。但是很多时候这个前提并不是那么显然,也不是那么容易得到,这个时候我觉得就只能反复的看,像编译器的 bootstrap 一样,这一次理解这么一点,然后和之前理解的结合起来再看下一遍。
    由于我的研究方向就是编译器,所以最近半年一直在读 LLVM 和 OpenMP 的代码。一开始的时候先 gdb 加断点看调用栈,然后再从这一点开始慢慢展开,一遍遍看,慢慢就来感觉了。有了这个感觉再从一个更高角度再去看,之前不理解的部分慢慢就又能懂一些了。这个过程就是一直不停迭代一直到全部理解。颇有一种深度学习那不停迭代最后收敛的感觉。
    levelworm
        13
    levelworm  
       2020-02-10 09:31:15 +08:00
    我觉得对于我这样的初学者来说,比较痛苦的就是怎么挑项目。其实代码质量好坏也无所谓了,反正太坏的也看不下去。但是主要的困难在于选取和自己水平恰当的源代码。也许初学者本来也不用看代码,还是需要有一定水平才需要看。
    zfish
        14
    zfish  
       2020-02-10 09:34:29 +08:00
    推荐使用 sourcetrail 阅读,体验还不错,对 C/C++/Java/Python 语言支持,其他语言还不行
    hyy1995
        15
    hyy1995  
       2020-02-10 09:39:51 +08:00
    我是找别人的技术博客看,先搞懂技术点的实现。

    如果一上来就直接去看源码,肯定蒙蔽。源码经过了好多年的迭代,里面有很多代码是补丁,或者是为了兼容性,真正的核心代码片段不是很容易单独提出来看。
    azcvcza
        16
    azcvcza  
       2020-02-10 10:01:06 +08:00
    针对问题去看吧。想想这些框架拿出来都是为了解决什么问题,如果不用框架你又会怎么解决,尝试造最小化轮子去试验功能,带着问题和解决方案去看估计会有点成效
    Leigg
        17
    Leigg  
       2020-02-10 10:06:50 +08:00 via Android
    先学会这个东西怎么用,并且足够好用,再从你使用的地方进入源码开始看。
    securityCoding
        18
    securityCoding  
       2020-02-10 10:50:17 +08:00   ❤️ 1
    一定带着问题看代码,脑子里面没有疑问看代码是没有作用的,反复复盘思考自己真的理解了吗?核心思路能自己独立实现一遍吗?
    netty
        19
    netty  
       2020-02-10 10:57:38 +08:00   ❤️ 1
    1.了解一下整体架构,相应的组成部分,以及各模板的大概作用。
    2.明确你阅读源码是为了目的?
    不要回答说就是为了学习,学习啥?太泛通常落实不了。容易失败,没有成就感,还受打击。

    由点到面去学习,每次只选一个点。这样,目标明确了,难度降低了,最后看懂了还能获得成就感,进入下一关。
    比如 1 )如何进行初始化 2 )如何监听端口 3 )如何实现单例 4 )如何动态扩容 5 )如何实现哈希
    3.写个 demo,调用一下 API,感受一下
    4.单步调试
    5.总结执行流程和关键代码
    qiumaoyuan
        20
    qiumaoyuan  
       2020-02-10 11:01:37 +08:00
    netty
        21
    netty  
       2020-02-10 11:06:25 +08:00
    @secondwtq
    王老师提到的,洞察到最关键的东西,最近刚好写了一篇文章,我觉得有点类似,分享一下:
    《掌握这些,你也能徒手实现 ArrayList、Vector 和 Stack 》
    https://mp.weixin.qq.com/s/zhDLb3vpbb70abXyFfucww

    不想看文章的,就看里面这段总结吧:
    写到这里,我们来总结一下掌握本篇内容的核心步骤:
    1.学会数组的基本操作,重点是插入、删除和扩容;
    2.基于数组的基本操作,完善并实现 ArrayList ;
    3.在 ArrayList 的基础之上,对所有方法加上同步原语 synchronized,实现 Vector ;
    4.继承 Vector,利用的几个基本方法,实现 Stack 的入栈出栈操作。
    通过以上几个步骤,能够更加高效的学习,更好的理解 ArrayList、Vector 和 Stack 这几个类的实现原理。
    netty
        22
    netty  
       2020-02-10 11:07:23 +08:00
    @qiumaoyuan
    最后还要尝试去对关键逻辑自己实现一下
    ofooo
        23
    ofooo  
       2020-02-10 13:55:28 +08:00
    要是王垠把他的几百行的深度学习框架开源出来就好了。。。。
    wanglufei
        24
    wanglufei  
       2020-02-10 14:10:23 +08:00 via Android
    @ofooo 怎么能让你偷学,然后出去装 X(手动狗头)
    Youen
        25
    Youen  
       2020-02-10 16:52:11 +08:00
    可以从测试入手, 跟着测试代码进去

    随便看看也是有收获的, 比如提高自己的代码"品味", 看到一些代码新姿势等..
    chenqh
        26
    chenqh  
       2020-02-10 17:00:36 +08:00 via Android
    看源代码我看的好慢,我看 tornado 断断续续看了一年,感觉还是生的不行
    encro
        27
    encro  
       2020-02-11 21:11:46 +08:00
    非常好的题目,根据你的题目我刚写了一篇短 Blog。

    如何通过阅读源代码学习?
    https://c4ys.com/archives/2034

    分为三个部分:
    1,有选择的阅读
    2,阅读步骤
    3,学习的要点

    总体思路是带着问题学习。
    YiyangILiu
        28
    YiyangILiu  
       2020-05-16 10:00:52 +08:00
    这个问题我也有感觉。我的想法是:

    1. 一定要带着好奇心和问题阅读框架,看得少没关系,看懂是目的
    2. 第一遍看最好手写一遍
    3. 看懂一步再看下一步
    4. 很多时候因为自己没参与封装的过程,经常出现看到一个点牵扯出三个新的不懂的点。或者更通俗地说,应该深度优先阅读还是广度优先阅读呢?我的方法是,只多看一层。
    比如 pandas DataFrame 类中一个 rename 方法( https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.DataFrame.rename.html),函数本身有 8 个 arguments,在 example 中用到了两个 arguments,别的都是默认。那我不熟悉这个方法的话,看 doc 不仅看用到的 2 个 arguments,另外的没用到的 6 个也要学学怎么用。但是更深入一层呢?比如 level 这个参数,如果不懂 pandas 中的 MultiIndex 概念是不能理解它的。那要不要为了理解这个参数去再深入一层,学习 MultiIndex 的概念和用法呢?这时就可以考虑一下,我既然没用过 MulitiIndex,我不理解没关系。这个简单的例子就是深度一层的含义。

    最近一直在阅读一个中小型框架的源码( github 总代码 6K 行左右),是深度学习方面的。这个框架的作用是用两行实现一个 2K 行左右的自然语言处理模型。
    其中第一行是实现一个分词器,也就是 tokenizer,这个 tokenizer 在框架内的实现大约 300 行,其内又有方法若干。第二行是实现一个语言模型,模型在框架内的实现大约 900 行。其内又有方法若干。
    最终,我使用好奇心和一点一点手写的办法,把这些给复现出来了。写完后发现自己很多一开始不理解的问题迎刃而解了。我对模型处理的流程比较理解了,让我复述一遍没问题。但是内部的数学运算还不能说特别理解,很多当时复现的时候就一知半解。

    比如 keras.backend.reshape()( https://www.tensorflow.org/api_docs/python/tf/keras/backend/reshape), tensorflow.einsum()( https://www.tensorflow.org/api_docs/python/tf/einsum),这些函数说实话不难,看例子都能看懂,但是当实操的时候,特别是操作一些四维的 Tensor 的时候,我就犯迷糊了,每个维度都有自己的物理含义,比如 sequence_length 是句子长度, hidden_size 是特征维等等。只能说不断地看不断学。

    我觉得之前一个答案说得好,看源代码就像迭代学习一样,每看一点就理解深一点,想看一遍就会基本不可能。其实世界上大多数事情都是这样,学习是个渐进的过程,特别是前沿的东西,都是在渐进中提高的。
    就比如 github 某个成熟项目源代码量 10k,但是翻 commits 记录,addition 至少是 lines of code 的 3-4 倍。10k 量级源代码,addition 40k 左右是正常的。不可能有哪个框架从 0 写到完成没有修改的。有经验的框架作者如此,学习者就更不能好高骛远了。
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   2886 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 36ms · UTC 09:04 · PVG 17:04 · LAX 01:04 · JFK 04:04
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.