今天上午,著名 AI 科学家 Andrej Karpathy 在 X 平台上分享了一篇文章,引起了广泛关注和讨论。这篇文章的核心论点是「认知负荷的重要性」,即在编写代码时,应考虑后续阅读者和维护者是否能更轻松地理解这些代码。Karpathy 强调这可能是最真实但最少被实践的观点。许多开发者喜欢在项目中展示复杂的技巧,甚至以花哨、难以理解为荣。然而,这种做法实际上增加了他人的认知负荷。
Hyperbolic 的联合创始人及 CTO Yuchen Jin 分享了一本书《软件设计的哲学》,指出复杂性是软件的主要敌人。书中将复杂性定义为任何使系统难以理解和修改的因素,而认知负荷是复杂性的重要组成部分。开发者 Aryan Agal 建议避免循环代码调用,让代码结构像树一样清晰。langwatch.ai 开发者 Rogerio Chaves 则认为中级开发者最喜欢增加他人的认知负荷,初级和高级开发者则尽力保持代码的清晰度。
认知负荷的类型及其影响
认知负荷是指开发者完成任务所需的思考量。当认知负荷超过一定阈值时,理解和解决问题会变得困难。例如,在修复一个完全不熟悉的项目时,如果项目使用了大量炫酷的架构和时髦的技术,这会给新开发者带来极大的认知负荷。因此,减少项目中的认知负荷至关重要。
认知负荷分为两种类型:
– 内在型:来自任务本身固有的难度,无法减少。
– 外来型:源自信息呈现方式,可以通过优化代码结构和命名等方式大幅减少。
复杂条件与继承的噩梦
复杂的条件判断和多层继承会显著增加认知负荷。例如,一段包含多个条件的代码可以通过引入有意义的中间变量来简化。同样,过多的继承层次会让代码难以维护,建议优先使用组合而不是继承。
小方法、类或模块太多的问题
小方法、类或模块虽然表面上看起来简单,但如果数量过多,反而会使项目难以理解。浅模块(接口简单但功能复杂)会导致开发者需要记住每个模块的功能和交互,从而增加认知负荷。相反,深模块(接口简单且功能强大)更容易理解和维护。
特性丰富的语言带来的挑战
编程语言的新特性虽然令人兴奋,但也会增加认知负荷。例如,C++ 语言的各种初始化方式和复杂的语法特性,使得开发者需要花费大量时间学习和理解。即使是经验丰富的开发者也可能会感到困惑,因为历史遗留问题和复杂的规则增加了额外的认知负担。
分层架构抽象的弊端
分层架构本应隐藏复杂性,但在实际应用中,它往往会增加间接性和跟踪难度。每次从一个调用跳转到另一个调用,都会占用有限的工作记忆空间,导致更多的认知负荷。因此,不应为了架构而增加不必要的抽象层,只有在实际需求时才添加。
领域驱动设计(DDD)的误解
领域驱动设计(DDD)旨在帮助开发人员、领域专家和业务人员有效沟通,但它经常被误解为一种具体的编码方式。实际上,DDD 更关注问题空间而非解决方案空间。如果不正确理解 DDD,可能会创建大量无关的认知负荷,给未来的开发人员带来困扰。
熟悉项目的认知负荷
新加入项目的开发人员往往需要较长时间才能熟悉项目的心智模型。通过衡量新开发人员的困惑程度(如通过结对编程),可以发现代码中需要改进的地方。保持较低的认知负荷可以让新人在短时间内为代码库做出贡献。
本文来源: 机器之心【阅读原文】