mcpField
M
m15-anti-pattern

m15-anti-pattern

github.com/actionbook测试与质量1.6k8.7k 次安装9 周前更新
代码仓库

关于 m15-anti-pattern

聚焦设计层反模式的 Rust 代码审查技能,将过度克隆、生产代码中使用 unwrap 等问题对应到替代方案和相关技能。

主要功能

  1. 01将反模式对应到替代方案
  2. 02检查所有权与错误处理
  3. 03将代码异味关联到相关技能
  4. 04提供 Rust 审查清单

适用场景

  1. 01审查 Rust 代码中的过度克隆
  2. 02查找生产代码里的 unwrap
  3. 03从借用检查器阻碍追溯设计问题

安装

复制下面的命令,在终端中运行。

$npx skills add https://github.com/actionbook/rust-skills --skill m15-anti-pattern

安装后在 Claude Code 中输入/m15-anti-pattern确认已加载。

附带文件patterns/common-mistakes.md

详细介绍

反模式

第 2 层:设计选择

核心问题

这种模式是否掩盖了设计问题?

审查代码时:

  • 这是在解决症状还是根因?
  • 有没有更符合惯用方式的做法?
  • 这与 Rust 的设计理念相悖,还是顺势而为?

反模式 → 更好的模式

反模式问题所在更好的做法
到处使用 .clone()掩盖所有权问题使用恰当的引用或所有权
在生产环境中使用 .unwrap()可能在运行时触发 panic使用 ?、expect 或错误处理
只有一个所有者时仍使用 Rc造成不必要的开销使用简单所有权
为了方便而使用 unsafe存在 UB 风险寻找安全的实现方式
通过 Deref 实现 OOPAPI 容易造成误解使用组合和 trait
巨大的 match 分支难以维护提取为方法
到处使用 String浪费内存分配使用 &str、Cow<str>
忽略 #[must_use]丢失错误处理结果或使用 let _ =

思考提示

看到可疑代码时:

  1. 这是症状还是根因?

    • 为了避免借用问题而克隆? → 所有权设计有问题
    • 因为“不会失败”而使用 unwrap? → 未处理边界情况
  2. 符合惯用方式的代码会是什么样?

    • 使用引用,而不是克隆
    • 使用迭代器,而不是索引循环
    • 使用模式匹配,而不是标志位
  3. 这是否与 Rust 的设计理念相悖?

    • 与借用检查器较劲 → 重新组织代码
    • 过度使用 unsafe → 寻找安全的实现方式

向上追溯 ↑

了解设计思路:

"Why does my code have so many clones?"
    ↑ Ask: Is the ownership model correct?
    ↑ Check: m09-domain (data flow design)
    ↑ Check: m01-ownership (reference patterns)
反模式追溯到问题
到处克隆m01-ownership谁应该拥有这些数据?
到处使用 unwrapm06-error-handling错误处理策略是什么?
到处使用 Rcm09-domain所有权是否明确?
与生命周期较劲m09-domain是否应该更改数据结构?

向下追溯 ↓

查看实现(第 1 层):

"Replace clone with proper ownership"
    ↓ m01-ownership: Reference patterns
    ↓ m02-resource: Smart pointer if needed

"Replace unwrap with proper handling"
    ↓ m06-error-handling: ? operator
    ↓ m06-error-handling: expect with message

初学者最常犯的 5 个错误

排名错误修正方法
1通过克隆绕过借用检查器使用引用
2在生产环境中使用 unwrap使用 ? 传播错误
3所有场景都使用 String使用 &str
4使用索引循环使用迭代器
5与生命周期较劲重新组织代码,让数据由当前结构拥有

代码异味 → 重构

异味表明重构方式
大量 .clone()所有权不明确理清数据流
大量 .unwrap()缺少错误处理添加适当的错误处理
大量 pub 字段封装被破坏改为私有字段 + 访问器
嵌套过深逻辑复杂提取方法
函数过长承担多项职责拆分函数
巨大的枚举缺少抽象使用 trait + 类型

常见错误模式

错误反模式成因修正方法
E0382 移动后使用混淆克隆与所有权使用恰当的引用
在生产环境中 panic到处使用 unwrap使用 ?、模式匹配
性能低下所有文本都使用 String使用 &str、Cow
与借用检查器较劲结构不合理重新组织代码
内存膨胀到处使用 Rc/Arc使用简单所有权

已弃用 → 更好的做法

已弃用更好的做法
基于索引的循环使用 .iter()、.enumerate()
先使用 collect::<Vec<_>>() 再迭代链接迭代器
手动实现 unsafe cell使用 Cell、RefCell
使用 mem::transmute 进行类型转换使用 as 或 TryFrom
自定义链表使用 Vec、VecDeque
lazy_static!使用 std::sync::OnceLock

快速审查清单

  • 每次使用 .clone() 都有合理依据
  • 库代码中不使用 .unwrap()
  • 有不变量的字段不公开为 pub
  • 迭代器可用时不使用索引循环
  • &str 足够时不使用 String
  • 不忽略 #[must_use] 警告
  • 使用 unsafe 时附带 SAFETY 注释
  • 不编写巨型函数(超过 50 行)

相关技能

场景参阅
所有权模式m01-ownership
错误处理m06-error-handling
心智模型m14-mental-model
性能m10-performance

评论

支持 Markdown