编程系统开发人员

描述 Rust 中如何处理错误。panic!、Result 和 Option 之间有什么区别?为什么 Rust 不使用异常?

用 Hintsage AI 助手通过面试

回答

在 Rust 中,没有像 Java 或 C++ 中那样常见的异常;相反,使用 ResultOption 类型作为错误返回的包装器。

  • Result<T, E> — 存储要么是值 (Ok(T)),要么是错误 (Err(E))。通常用于可能不成功的操作(例如文件输入输出)。

  • Option<T> — 用于可选值:要么是 Some(T),要么是 None,没有错误信息。示例:

fn divide(x: f64, y: f64) -> Option<f64> { if y == 0.0 { None } else { Some(x / y) } }
  • panic! — 引发程序崩溃,格式为“致命错误”或“assert”。应仅在违反不变性时使用,而不是处理用户错误。

Rust 中没有类似 try/catch 的异常,以确保透明、可控的错误流,并且不需要垃圾回收器或展开引擎来维护异常。

反问

为什么 panic! 不应用于常规错误处理?

答案:panic! 会终止执行流,没有恢复的机会,导致回滚/中止。如果错误通过 Result 返回,调用方可以处理它们。示例:

fn foo() -> Result<(), String> { Err("发生了某些错误".to_string()) } // 而不是 fn foo() { panic!("发生了某些错误"); }

由于缺乏对主题细节的了解而导致的真实错误示例


故事

在一个处理图像的微服务中,开发者使用 panic! 处理所有异常情况。这导致服务在任何错误时崩溃,而不是向客户端返回详细的 HTTP 响应。


故事

在一个 CLI 工具中,对所有输入输出使用 unwrap(),而没有处理潜在的错误。结果是,文件系统错误时程序直接终止,没有任何消息或诊断。


故事

在一个分析服务中,试图用 Option 处理每一个细小的错误,失去了错误信息,调试变得困难。转而使用具有错误枚举的 Result 后,查找和修复 bug 更加简单。