FP Best Practices 是一个专注于日常函数式编程决策的技能,目标是塑造代码的可组合性、可预测性和长期可维护性。它特别适用于以下任务受益的场景:纯逻辑与副作用之间更清晰的分离;将小型函数组合成管道;用类型使非法状态不可表示;以数据变换替代可变修改;以及引用透明性和更轻松的测试。
工作风格方面,该技能倡导为下一个阅读者编写函数,而不仅仅是为运行时;将副作用保持在边缘,保持核心纯净;优先选择小型、可组合的函数,而非聪明的一体化实现;使用类型和名称揭示意图;在数据结构能够胜任时让数据结构发挥作用。
审查工作流包括:识别变换(什么数据进入、什么出来、该函数建模什么领域概念);检查纯度(函数是否有可观察效果,如 I/O、对调用方拥有或共享状态的更改、随机性;副作用能否推到边界);检查组合(函数是否只做一件事、能否表示为更小函数的组合、能否在其他管道中复用);检查类型和边缘情况(null/undefined/错误情况是否通过 ADT 显式处理、返回类型是否诚实反映可能失败);应用最轻量的有用改进(提取函数、引入 pipe/compose、用 Maybe/Option 替换 null、用 Either/Result 替换 throw、将副作用推到边界、用 map/filter/reduce 替换循环)。
额外的审查视角包括:纯度与引用透明性(纯函数对相同输入总是返回相同结果,易于测试、组合和并行化;不纯操作如 I/O、日志、随机、时间属于系统边缘);组合优于命令式顺序(当管道能阐明数据流时使用管道,当命名中间步骤或局部循环更易理解时保留它们;小型函数结合 pipe 或 compose 揭示变换形状;当数据流已从管道清晰可见时,无点风格可去除噪音);代数数据类型优于 null 和异常(当值可能合法缺失时使用 Maybe/Option;当操作可能失败且调用方需要错误时使用 Either/Result;将领域变体建模为标记联合类型而非可选字段);不可变性作为默认(保留调用方拥有和共享状态;私有累加器若不逃逸则可观察为纯;使用 Object.freeze、readonly、不可变记录或持久数据结构;对调用方拥有或共享状态的修改是效果,永不逃逸的私有状态可保持可观察纯度);高阶函数作为词汇(map 变换结构中每个元素而不离开结构;filter 按谓词选择元素;reduce/fold 将结构折叠为单个值;flatMap/chain 对每个返回包装值的计算进行序列化)。
日常规则包括:优先纯函数,将不纯操作提取到边界;按执行的变换而非机制命名函数;使用 pipe(从左到右)或 compose(从右到左)表达数据流;用 Maybe/Option 或项目原生等价物建模有意义的缺失,保留既定边界契约;当调用方需要处理失败时用 Either/Result 替换 throw;当部分应用使调用点更清晰时柯里化函数;优先不可变值,将必要修改保持私有于其所有者或在效果边界显式化;优先揭示意图的变换,当管道模糊算法或增加实质复制成本时局部循环是有效的;保持函数小型——一个变换、一个抽象层次;使调用间持续的状态显式,改变此类状态的闭包影响后续观察。
良好信号包括:每个函数仅用其输入即可测试,无需设置;管道读起来像问题描述;非法状态无法从类型构造;副作用局限于清晰命名的边缘函数;更改一个变换不会破坏无关管道。警告信号包括:函数修改其输入或外部状态;null 或 undefined 作为有意义的哨兵值传递;异常用于正常控制流;长函数混合数据获取、变换和输出;可变共享状态通过函数参数传递;map/filter/reduce 能使意图更清晰的 for 循环;混合逻辑与 I/O 的深层嵌套回调或 .then() 链。
参考文件方面,该技能提供多个参考文档:typed-boundaries.md(选择更强类型、验证外部数据、权衡局部修改与管道时)、core-principles.md(纯度、不可变性、引用透明性和组合等基本 FP 原则)、naming-and-abstractions.md(命名或抽象质量为主要问题时)、function-composition.md(pipe、compose、柯里化、部分应用和无点风格)、algebraic-data-types.md(Maybe/Option、Either/Result、标记联合和使非法状态不可表示)、managing-side-effects.md(IO 边界、Reader/Writer/State 模式和效果系统)、higher-order-functions.md(map、filter、reduce、flatMap、转换器和函子/单子模式)、language-examples.md(语言特定示例文件索引和快速参考表),以及 JavaScript、TypeScript、Python、Go、Rust、Haskell、Elm、Clojure、F#、Elixir 的示例文件。
相关技能方面,当代码库混合 FP 和 OOP 且对象设计存疑时使用 oop-best-practices;将 FP 引入现有命令式代码库时使用 refactoring-best-practices;评估模式是否映射到函数式等价物时使用 design-patterns-best-practices;测试驱动纯函数和效果边界时使用 tdd-best-practices。
来源影响包括:Mostly Adequate Guide to Functional Programming(Brian Lonsdorf)、Haskell Programming from First Principles(Allen & Moronuki)、Structure and Interpretation of Computer Programs(Abelson & Sussman)、Functional Programming in Scala(Chiusano & Bjarnason)、Domain Modeling Made Functional(Scott Wlaschin)、Grokking Simplicity(Eric Normand)以及 fp-ts、Effect-TS 和 Ramda 库文档。
使用方式:该技能以参考指南形式提供,开发者可在设计、审查或重构代码时阅读相应参考文档,并应用审查工作流和日常规则。它不提供自动化工具或代码生成功能,具体安装命令和平台信息暂未提供。限制方面,该技能假设读者具备一定的函数式编程基础,且示例以多种语言呈现,实际应用需结合项目上下文和语言特性。