代码背后的目的是否“惯用”以减少认知开销?


22

我试图向某人解释,他们编写代码的方式很难理解,并且如果您重构它,那么它更容易阅读。我正在使用的这种代码风格通常称为“惯用代码”。

但是,惯用代码一词带来了道德上的正确性,这并不是促使人们改变其编码风格的巨大动力。一种更积极的说法是遵循通用样式的代码 -但对于批判性思想家来说,这种想法是随众而为的。

我提出这个想法的方式可以激发人们更改他们的代码:

  • 以减少读者认知负担的方式编写代码(例如,我不记得这是第一类矢量还是第五类矢量)
  • 易于理解意图的代码(例如,此向量的作用是什么?)

(顺便说一句,我知道《 Clojure的喜悦》一书在其首次发行之前就具有标题“ Idiomatic Clojure”的草稿。因此,这似乎是使代码“惯用”,从而为读者“带来喜悦”的原因。 )。

我的问题是:代码背后的目的是“惯用的”以减少认知开销吗?


我对阅读代码的典型评论是,您至少为两个编译器编写代码:包括您自己在内的其他人必须稍后阅读代码。以及您通过Ant,Make或IDE运行的过程。第一个更重要。

Answers:


19

首先,我不确定“惯用”一词中是否存在任何“道德正确性”。在普通字典中的定义是根本

特定语言或方言特有的或特有的:惯用的法语。

是的,惯用代码通常会减少认知开销,尤其是在接口定义中,项目所需的标准库和任何第三方库(实际上)都是惯用的。

不过,作为卖点,我将专注于减少认知开销对您的影响。这使程序员更容易发现错误,因为他们没有试图拆开以独特风格编写的代码来找出错误被精巧之处或处理不当的情况。这样可以更轻松地检查其他人的代码,从而使团队更有可能进行真正的检查来识别实际问题,而不是争论语法。

除了减少认知开销之外,惯用代码通常是更有效的代码。特定语言中的大多数惯用语都会演变,因为该语言旨在以特定方式解决问题。您使用的编译器或解释器会将优化重点放在惯用代码上。例如,如果您使用一种语言,其中递归是结构代码的惯用方式,那么您几乎可以肯定编译器实现了尾递归。如果您使用的是非惯用递归的语言,则可能性要小得多。尾部递归不可能在任何地方都无法实现,但是大多数编译器作者不会将注意力集中在不常发生的事情上。


1
您的回答相当合理,可以激发这种反应:来自巴黎,蒙特利尔,科特迪瓦的惯用法语?代码没什么不同。没有社区就没有成语。如果您听起来像蒙特利尔,可能会在巴黎引起一些“认知超负荷”。可能世界总是会被认为存在单一正确方法的人(Python?)和说“区别对待”的人分开!(JavaScript?)。现在,如果我们想编写让编译器发现更有效的Javascript习惯用语,就让我们都像压缩程序/ uglifier一样编写!
joshp

值得庆幸的是,当V8发布时,设计师们决定不再玩人工微基准测试游戏,并创建了模拟真实世界,精心设计,精心设计的惯用代码的基准,其他供应商也纷纷效仿。这导致了性能游戏中的角色颠倒:在程序员为了表现而编写代码之前,程序员的工作是轻松的工作;现在,为性能而设计其编译器是程序员的工作,这样程序员就可以轻松完成工作-应该是这样。
约尔格W¯¯米塔格

很好听的鲱鱼,但口语共享地理限制,计算机语言则没有。因此,您的观点有些争议。更不用说将Python和JavaScript与Parisian和Montreal的方言进行比较了。(我不确定Python程序员或蒙特利尔居民谁会冒犯更多人?; D)。
Marco Marco

10

我不知道您会认为成语具有任何道德内涵。成语只是表达事物的一种方式。它们是模式,其规模大于单个单词或短语。

如果我告诉过你一个人必须对狼how叫,即使我知道这是德国的一个成语,您也不知道我的意思。如果OTOH,我告诉你,在罗马的时候像罗马人那样做,那么你会立即知道我在说什么,因为我使用了正确的英语习语。

计算机语言没有什么不同。

实际上,在编程世界中,“惯用语”的替代名称是“实现模式”。这与构想有关,该构想来自建筑师(克里斯托弗·亚历山大(Christopher Alexander))(实体而不是位)。大多数程序员都知道设计模式,有些则知道体系结构模式,这些模式的规模大于设计模式。成语是规模小于设计模式的模式。


5

大多数语言都故意使自己具有特定的风格。用这种风格编写的代码是惯用的。如果您忽略了运行时环境的选择会缩小语言选择范围的情况,那么您应该选择语言,因为眼前的问题很容易用语言的特定习语来表达。

大多数人都没有。例如,许多Java程序员在必须编写JavaScript时会努力保持相同的风格(请注意,他们可能已经编写Java并对其进行交叉编译)并在某种程度上取得了成功-在JavaScript中编写了Java惯用的代码-但是他们总会有与JavaScript对抗的感觉。缺少某些功能或很难模仿它们。

惯用的代码很好。局外人很难,但他们可以学习。最终,代码必须维护数年,因此,如果您可以在惯用语言中找到一种语言,可以用简单的方式表示基础程序,那么您应该这样做。

让我澄清一下,肯定有过度使用成语(或潜在的语言功能)之类的东西。如果您使用C ++模板在编译时执行应用程序逻辑的重要部分,或者您的完整Lisp程序是对某个宏的调用,而该宏以一种几乎无法预测的方式展现给实际事物,那么您的简单问题的Java解决方案会膨胀为FizzBu​​zzEnterpriseEdition的比例...您做错了。

人们说代码必须易于阅读。那只是真相的一半。它必须易于理解,这也要求它也易于推理。这就需要适当使用抽象。与大多数事情一样,这是达成适当平衡的问题。


我希望我可以再为该FizzBu​​zzEnterpriseEdition链接
再加
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.