0%

纲领、意图、语义:从接口设计到公司治理

TL;DR

  1. 为什么接口设计要表达清晰明确的语义?
  2. 为什么一次代码修改(cl/pr/commit)要有唯一明确的意图?
  3. 工作中为什么要树立自己的人设?
  4. 如何让 OKR 发挥作用?
  5. 如何三句话让客户为你的产品花钱?

智人的局限性:

  1. 每次只能做好一件事,记住一句话。
  2. 习惯机械地保持言行合一,且善于自我辩护(《影响力》)。
  3. 面临过多不确定性时难以做出决定(《影响力》)。

这些局限性每天都在影响着我们中的每个人,使得我们:

  1. 事情多了就容易忘、走神、效果不好。
  2. 没有明确的目标就会茫然、缺乏动力。
  3. 面对不了解的事物时缺乏勇气、动力,难以做决定。

相信我,在座的各位,在这些方面,很难不被称为垃圾。

承认这些局限性是我们取得胜利的第一步,第二步则是利用这些局限性驱动自己(或引导他人)做出更有利于我们的行动。

如何利用这些局限性?

  1. 突出目的,用尽量少的记忆量表达尽量多的信息量,有利于智人们在它们有限的记忆力/专注力范围内做好尽量多的事情。
  2. 公开表达自己的意图,减少潜在的不确定性,帮助智人们更容易做出决定。
  3. 公开自己的纲领,并坚持下去,智人们自然会根据它看到的纲领调整自己的姿势并自觉拥护。

总之,把问题简化,对谁都好。

以下讨论的主题从接口设计到公司治理,并没有什么新鲜的结论,只是试图从中归纳出一种统一的方法论。这很符合本文的主旨。

为什么接口设计要表达清晰明确的语义

接口设计要遵循什么原则?“高内聚,低耦合”。

什么叫“高内聚”?不同的元素之间,必要的交互越多,它们的聚合性(或称耦合性)越强。反之,就是“低耦合”。

我们可以把一个程序/系统看作一张图(Graph),每个元素看作一个顶点,元素之间的交互看作一条边。则接口设计、模块分割、微服务化,都在做着同一件事:聚类。我们找到一个元素集合,如果这个集合内部的聚合程序很高,但与外界的交互很少(或很统一),就可以将它视为一个整体,一个新的元素放回到图中。

重复这个过程,元素的粒度由细到粗,从函数,到类,到模块,到服务,等等,图的复杂度越来越低,直到符合智人的脑容量。此时,神奇的事情发生了。每次只能做好一件事,记住一句话的智人,可以不费力地理解一个庞大的系统(想象一下一个分布式的、微服务化的业务系统,如果细化到具体的函数,该有多复杂多庞大)。天哪,这么神奇的吗?

回看整个过程,我们可以找到其中最核心的一个操作(反复扣题),聚类。聚类意味着我们可以将多个元素的行为(或称语义)叠加起来,仍然视为一个元素,且只消耗智人相同量级的记忆量。这就需要我们为这些元素归纳出一个清晰、明确的语义。一句话,让你懂,尽管背后藏着千千万万的细节。

code review 时,有些听起来很 naive、很不高端的问题:

  1. 提出这个类的目的是什么?它有什么作用?
  2. 这些参数都是必要的吗?有没有重复的、可以由其它参数推导出来的部分?
  3. 为什么需要这个接口?
  4. 考虑到对称性,为什么不增加另一个接口?

是 reviewer 不懂吗?不一定,TA 也许只是为了减少未来读者(包括自己,也包括 1s 后的作者)的理解难度。给定一个类/模块/服务的名字,如果底下某个接口需要额外的解释,这个设计就还有提高的余地;如果每个接口都需要额外的解释,这个设计就是一次失败,会被无数次地用错、吐槽、直到被重构或抛弃掉。

总结:接口设计需要表达清晰明确的语义,争取一句话讲懂,多一句都差评。

为什么一次代码修改(cl/pr/commit)要有唯一明确的意图

  • CL:Change List
  • PR:Pull Request
  • Commit:问 git 去

系统是由一次次代码修改组成的。我们要保证每次修改都可以用一句话描述,就需要它有唯一的、明确的意图。为什么?因为代码修改需要被阅读、被推理、被 review,而这些操作的另一边都是可怜的智人。而这些智人又通常是团队的瓶颈:人数越多,代码修改的生产速度越快;但 reviewer 通常跟不上这种速度。

行数通常是 code review 速度的一项关键因素:

  1. 一个 50 行的代码修改,通常扫一眼就清楚了;
  2. 500 行的代码修改就需要随手准备个小本本画一下依赖关系;
  3. 5000 行的代码修改则必须要拉上作者讲下前因后果,一点点抠了。

然而行数不是唯一因素。一个很长的代码修改,如果意图明确,不会很难读;混杂了多种意图的代码修改,即使并不长,也明显增加了 reviewer 的精力消耗。举几个例子:

  1. 5000 行的 code format 不怎么消耗 reviewer 精力,看一眼就可以放过。
  2. 5000 行的 code format,但里面夹杂着一个 bugfix 就要了亲命了,reviewer 需要一行一行仔细阅读。
  3. 既移动代码又对代码进行微小的功能修改,在现有的鶸 review 工具下,需要 reviewer 自己左右打开两份代码,手动对齐,再一行行对比。要是其中再加个函数拆分,谁爱看谁看,反正我不看。

唯一的代码修改意图(refactor 还是 feature 还是 bugfix)避免了 reviewer 的精力浪费或不该有的忽视,该精读的能精读,该略读的能略读。

接下来,常见的工作流程也要求代码修改的目的要单纯:考虑到 cherry-pick,一个代码修改最好不要包含无关的内容。

最后,唯一的代码修改意图也在展现着作者的能力,我有能力总结出一种意图,且将其具象化为一次代码修改,这不失为一种“太成功了”。顺便,这样也不容易搞出乌龙(如写出低级 bug),在众人面前丢人。

总结:一次代码修改需要唯一的、明确的意图,为他好,也为你好。

类似地,一个项目也要意图明确,三意二心的项目往往半途而废。

工作中为什么要树立自己的人设

瑞·达利欧在《原则》中说,组织架构最好是树状的,每个子树都要有清晰的功能定位。如前所述,这也是一种聚类。现在,我们翻转一下问题,你,作为树中的某个叶子节点,如何获得满意的功能定位?

我的答案是,要有人设。

团队中每个人都有自己的人设。A 技术很 NB 但做事没规划;B 啥都能做,还能为老板抗事儿;C 能力有限,但很细心,总能按时完成;而你,D,没有特点。

你怎么可能没有特点呢?你的野心(或称上进心)在燃烧,你也有自己的得意之处,你每天苦恼英雄无用武之地。但你缺少人设。人设是对一个智人的接口的一句话描述(又扣题了),你的所有内涵、能力、性格,最终也只能被归纳为一句话。这句话,就是别人想起你的第一句话。

相信我,大多数主管不是坏人,他不是不给你好活,只是不知道该给你什么活合适:

  1. 给需要深度的,怕你不会;
  2. 给需要审美的,又不了解你;
  3. 给有时限的,怕你耽误事儿。

于是,最后只能把你归为“其它”,给你别人挑剩下的活。好心的主管给你简单但无关紧要的活,不那么良心的主管就给你谁都不想要的活。

想改变这些,从立人设开始。你总是有擅长之处的,把它表达出来,告诉周围的人,告诉主管,说你想做,而且会做 xxx。立人设也是一种公开承诺。如前所述,智人拥有这种言行一致的倾向,当你立起人设了,你就会有自发的动力去维护它,这反过来会促进你强化这一人设,去学习必要的知识,练习相关的技能。立人设也可以简化主管面临的任务分配:现在的你对于他来说就不那么不确定了,他更容易做出决定。

除了与主管的交互,当你立起人设后,同事之间的交互也会更简单、更顺利。类比良好的接口设计,你建立人设的过程,就是在完善自己对外的接口。这套接口越好用,其他人越乐于使用。

接下来,立人设也不需要担心是否会把自己限制住。随着你的能力积累,其他人归纳你的方式也会变化,粒度越来越粗,从“擅长 xxx 问题”,到“技术大牛”或“项目推进大师”。智人们总是会用一句话来描述你的,别让这句话太无聊。

立人设并不是一劳永逸的,你需要长年累月的积累、坚持,稍不留神还有翻车的风险。但这很值得。

总结:立人设也是一种接口设计;它能简化交互,消除未知,降低主管与同事与你交互的难度;同时它是一种公开承诺,你会更有动力维护你的公开承诺。

如何让 OKR 发挥作用

一个组织需要一个公开的纲领,否则无法保证成员的凝聚力。

这句话是几年前从知乎上看到的,当时有人大概问了这么个问题:为什么一个政党不能隐瞒自己的意图。但现在找不到了。

(涉及政治的部分就略过吧……)一个公司是一个组织,它也需要一个公开的纲领。

工作几年以后,我们往往会把工作视作一种庸俗化的等价交换,你用自己的时间,从老板那里换钱。这种逻辑没错,但对于公司而言,只存在这种等价交换是非常危险的:公司需要员工的一部分超额劳动。

如果工作只是工作,这种超额劳动只能归为一种资本家的压榨。但有趣的是,很多智人会在工作中获得一些满足感,他们可能会把工作视为爱好,视为社交,最终主动地奉献一些超额劳动。很难说这算不算是智人的另一种局限性。我很认同一种观点,不要把工作与生活截然分开,去寻找那些你休息时仍然愿意做的工作。

成功的公司都或多或少意识到了这点,他们会想尽办法用最小的花销最大化提升员工的满足感、参与感,如免费零食、舒适的工作环境、定期的团建(翻车概率大)等。这里我们讨论公司的纲领,也就是 OKR。

OKR 是什么?它是一种方法论,你瞄着一个目标,制定计划,最终将结果拿来和目标对比。一个公司有整体的 OKR,老板会瞄着这个目标,制定自己的计划。顺着组织架构,部门可以瞄着公司的 OKR 制定自己的 OKR,部门总监据此制定自己的计划。接下来是团队、个人。

这个过程是自顶向下的,公司有一个纲领,一个目标,接下来每个部门、团队、个人,都根据自己所在的位置看到的这个目标的样子,制定自己的计划。这个过程中,每一级都只需要、且只能看到自己以上的 OKR,而不需要、也不应该关注自己以下的 OKR。大家都在朝着一个目标,只是因为所处位置不同而产生了不同的计划。这就是我对 OKR 的理解。

相比而言,KPI 则是自底向上的,每一级都盯着自己的下级,将自己的目标分解为下级的目标。这个过程中每个人不需要关心更上一级的目标,只要完成自己的目标,明码标价,童叟无欺,只是没有了那种凝聚力。

为了让 OKR 发挥作用,我们需要:

  1. 纲领要公开,不要藏着掖着。
  2. 纲领要明确、简短,让人看一次忘不了。
  3. 纲领要能坚持不动摇。
  4. 每一级都要明确地朝着这个目标制定计划,中间一旦掺杂了私货,下面各级都会走偏。

一个公开的纲领就像一座灯塔,可以为整个公司指引方向。这种明确的、唯一的方向的重要性不言而喻。电子的运动方向越集中,电流强度越大。公司的方向越集中,内耗越小,成员之间的协同效应越强烈,整体执行能力越强。这种成功反过来又可以提升众人对纲领本身的认可程度。

公开的纲领的另一个好处是可以筛选掉那些不认可它的员工。大家道不同不相为谋,不是坏事。反倒是不同思想的激烈冲突(或曰内耗)既耽误了员工,又影响了公司。

纲领本身一旦被公司成员所认可,如前所述,智人善于自我辩护,公司成员就会反过来为纲领辩护。这种辩护也是凝聚力的一部分。而凝聚力越强,公司抵御风险的能力越强,越能克服困难,在险恶的环境中生存下来。

如果公司还能将纲领坚持下去,言行一致的本能同样会提升众人对纲领的认可程度。

最后,所有这些的前提是,整个公司都能看到相同的纲领。如果有人将 OKR 替换为局部的等价交换,上述推理链就不复存在了。做个不恰当的类比,一个是“同志们跟着我冲”,一个是“弟兄们给我顶住”。

总结:一家公司需要一个统一的、公开的纲领,它能以低成本的方式增强员工的凝聚力,减少内耗,提升执行能力。

以上内容中,将公司替换为部门、团队仍然有效。

如何三句话让客户为你的产品花钱

最后顺便提一下产品定位。

一款产品,如果不能在几句话中讲清楚它的价值,就离失败不远了。智人那可怜的耐心与脑容量,当面对长达几页纸的产品介绍时,显得那么无助。你有且只有一次机会,用三句话,讲清楚产品的价值所在,接下来趁客户的脑细胞兴奋时,再去灌输那些细节。

这样来说,一款产品也要服务于一个目的。如果定位 TiDB 是一个关系型数据库,那么集成数据湖类的功能就显得很尴尬;而如果定位 TiDB 是一站式的数据处理平台,那么任何可以简化客户数据处理流程的功能都是在服务于这个目的。

一个需要增加一句话来解释的功能,会让这个产品更尴尬,而不是更强大。

总结:P 社加油。