Giter Club home page Giter Club logo

zen-coding-notes's Introduction

禅意编程札记

基本编码习惯

  • 写出能解决问题的程序有100种方法,但是优秀的工程师能找到最好的一种。
  • 代码自描述
    • 代码是写给人看的,不是写给机器看的,只是恰好能运行而已
  • 每条语句皆有作用,不做无谓的赋值
  • 减少上下文依赖,编写显而易见是正确的代码
  • 最小化参数要求
    • 传ID就能解决问题的时候不需要传对象
  • 减少函数内多余的中间变量
    • 减少中间变量的命名的意义
    • 直接return
  • 在一个作用域内,变量的类型保持不变(仅对脚本语言)
  • 不要滥用语法糖,少用奇技淫巧

项目工程

  • 如果你的整体代码结构变得极其复杂,往往是产品需求有问题
  • 从整体到细节,自顶向下的工作顺序
    • 基础库的编写顺序,优先写 guide / example
  • 全新的业务工程,先不考虑架构
  • 好的代码不是写出来的,是重构出来的
    • 在项目发展的合适时机进行重构,项目规划过程中应该留出明确的重构时间
    • 这份札记是如何编写出来的
    • 重构的过程中不一定要保证每次修改均可运行

逻辑控制结构

  • 防御式编程
  • 循环结构优化
    • 不同的语言有不同的最佳实践
  • 不要轻易使用while(true)
  • 错误和异常是常态,错误处理像业务代码本身一样必不可少

代码拆分规则

  • 原子化函数
    • 举例,微博三步授权流程代码
  • 业务逻辑分层
  • 最好的代码拆分方式是,清晰定义每一层的程序各自解决什么问题,不关注什么问题
    • 基于清晰的分层原则,即使在很多类里面出现一行代码的函数,你也会非常自信地认为这是合理的
    • 如果无法定义分层,就只能根据代码复杂度来拆分。通常情况下,这是因为你的理解还不够深刻,或者需求的复杂度还没有充分展开。
  • 类的层次
  • 什么样的代码应该写成独立业务,什么样的代码应该写在公共流程中(并加启用条件)
    • 如果使用率很高,就写在主流程里
    • 如果只是业务的一个分支,则不应该给主程序增加复杂度
  • 不要把业务相关代码和基础库代码混在一起
    • 始终以要开源的标准去写基础库,绝不耦合业务逻辑
  • 业务逻辑的不同层次的实现方式
    • 大量需要变更和管理的业务,存在数据库
    • 很少更新,并且无逻辑的,写在配置文件里
    • 很少更新,但是有逻辑的,写在独立的程序文件里
    • 尽量不要写在主程序里
  • 一个功能全面的大方法还是多个功能简单的小方法
    • 与其用复杂的配置参数,不如用多个简单的原子化方法
    • 然后写一个通过多个原子化方法实现功能的shorthand方法
    • 善用fluence interface
    • 如果一个函数要接受5个以上参数,你可以先想想这些参数真的是用来解决同一个问题的吗?
  • 什么情况下用配置文件的方式接受配置,什么情况下用函数来接受配置?
    • 配置文件虽然看起来不需要编程,但实际上额外需要一份冗长的配置参数文档
    • 配置文件方式限制了灵活性,但保证了安全性,适用于提供给对外部用户的功能
    • 函数方式提供了更强的灵活性可塑性,比如TensorFlow之于Caffe
    • 函数方式要求使用者具备编程能力,适用于中间件,适用于需要二次开发的场景
  • 除非有特别需求,提供一种初始化/配置方法就够了,不要玩参数列表的花活
  • 一个可以处理多种情况的多if-else函数,还是处理单一情况的简单函数
  • 区分有状态对象和无状态对象
  • 类内尽量少维护状态变量
  • public的方法必须在自己函数体内完成对所有状态变量的维护
    • 所有public方法,调用前和调用后,类的状态应该是自洽的
  • shorthand方法
  • 不要在局部函数里修改全局变量
  • 如果你很难给某个函数起名字,往往是因为代码拆分有问题
  • 如果你很难给某个类起名字,可能这个类就不应该存在
  • 对于脏的输入,明确地在一层代码中做参数校验,而在后续的代码层中完全信任传入的参数,因为都已经被校验过
  • 正确看待封装
    • 不要为了封装而封装
    • 封装的时候,最重要的不是选择隐藏什么细节,而是暴露什么细节
    • 不要惧怕学习,或者阻止别人学习。不要为了避免别人的学习而封装

问题跟踪和解决

  • fail-fast
    • 服务端,如果请求hang住会导致服务器被打满,需要尽快把有问题的请求抛弃掉,保证普通请求的正常执行
    • 引申,如果有错误,不要遮着掩掩,而应该让错误及时暴露出来,更早发现更快解决
  • 如果这个问题可以在开发过程中被发现并解决,就不是什么问题
    • 不要在代码里为不会使用API的程序员报错误
  • 开发过程中,应该让错误出现得越明显越好,能crash能抛异常,而不要静默处理
  • 用户层,不要掩盖错误细节,至少提供错误码或者保存日志

复用,还是冗余?

  • 什么样的代码应该写成函数?
    • 不是代码写了两遍就需要写成函数,而是这个函数有明确的功能和清晰的参数列表
    • 不要因为一段代码只写过一遍,就不抽成函数
  • 合理冗余代码
    • DRY原则永远是对的吗?
    • 少写代码并不是架构设计的主要目标,甚至都不是目标
    • 明智而自豪地复制代码
    • 面向未来编程,如果两段代码目前很相似,但未来会分化,就不要复用它
  • 三行以内的代码不值得复用
  • 不要因为自己查资料写出了一段自己原来不会写的代码,就一定要把这段代码抽成函数
  • 恶心自己,方便大家
    • 类的内部合理冗余代码,外部调用足够简单
  • 复用的代价
    • 实际处理过程被隐藏
    • 灵活性损失
    • 性能损失
  • 通用和性能之间的平衡点
  • Lazy Load
    • 在用户主路径上的业务和开销极小的业务不需要 Lazy Load

命名

  • 变量名的原则
  • 变量的命名要符合上下文场景
    • 一个参数传递的链条中,不一定是同一个名字
  • 学好英语,起好名字
    • 用意义准确的特殊词,少用组合词,比如: SiteUser -> Member
    • 英文动词不只有get和set,用好动词准确表达
    • 正确使用单复数
    • 梳理出明确的命名原则
  • 建立一个产品概念到开发概念的映射词典
  • 能用批量替换解决的问题,就不是问题

注释

  • Don't comment WHAT, comment WHY.
  • 不要寄希望于用注释来解释清楚代码
  • 和业务相关的脏代码必须注释
  • 删除历史遗留代码,而不要注释它
  • 善用 FIXME, TODO 等特殊注释关键词,以便日后检索整理方便

面向对象的设计原则

  • 多层继承还是多个独立的类
    • 尽量在一个类中呈现出完整的业务逻辑,同一个层次的业务逻辑,不要写在不同层的类中
    • 多层继承的代码可读性和可维护性远比你想象得要糟
  • 善用trait/mixin
  • 每一个public函数的切面,整个对象状态都自洽
  • 将对成员变量的变更和维护,集中到有限几个函数中,原子化的功能函数不维护状态变量

目录结构和文件命名

  • 用唯一确定的属性作为定位的规则,避免歧义
    • 按层放置文件
  • 文件名和类名有一致的对应规则

安全和可靠性

  • All Input is Evil
    • 所有来自用户自由输入的参数,都必须检查

PHP技巧

  • spl库的运用
  • yield的运用
  • 命名空间的运用

Javascript技巧

Web服务技巧

zen-coding-notes's People

Contributors

hikenote avatar shen2 avatar zhiwuba avatar

Stargazers

 avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.