为什么 Rust 中的测试并不可怕,反而很有趣?
\n\n当你刚开始学习 Rust 时,似乎编译器已经为你完成了所有脏活累活。它检查内存、跟踪借用,防止你搬起石头砸自己的脚。但即使是最严格的编译器也无法检查程序逻辑。这正是测试发挥作用的地方。
\n\n许多初学者害怕测试。他们觉得这是浪费时间,需要编写大量枯燥的代码。但实际上,测试是你的安全保障。它们帮助你更快地发现错误、自信地进行代码重构,并在发布后安心入睡。
\n\n在本文中,我们将探讨如果你是初学者,如何开始 Rust 测试。没有废话——只有实践、真实示例以及在实际项目中会用到的建议。
\n\n开始前需要了解什么?
\n\n在编写测试之前,请确保你已经安装了 Rust。如果没有,请打开终端并执行:
\n\ncurl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh\n\n我们所需的一切都已经内置在生态系统中。无需安装任何额外的框架。Rust 提供了一个强大的内置测试运行器,只需一个命令即可启动。
\n\n创建一个新项目来进行实验:
\n\ncargo new rust_test_guide\ncd rust_test_guide\n\n太好了!现在我们有了一个干净的项目,可以在其中学习编写测试。
\n\n第一个测试:通过示例来理解
\n\n打开文件 src/lib.rs。默认情况下它是空的,但我们将添加一个简单的函数及其测试。
让我们编写一个检查数字是否为偶数的函数:
\n\npub fn is_even(num: i32) -> bool {\n num % 2 == 0\n}\n\n#[cfg(test)]\nmod tests {\n use super::*;\n\n #[test]\n fn test_is_even() {\n assert_eq!(is_even(4), true);\n assert_eq!(is_even(7), false);\n }\n}\n\n逐部分分析代码:
\n\n- \n
#[cfg(test)]— 这个属性告诉编译器:“仅在运行测试时编译此模块”。它不会进入最终构建。 \n mod tests— 我们创建一个测试模块。这是标准做法。 \n use super::*;— 导入上面声明的所有内容,以便看到我们的函数is_even。 \n #[test]— 一个标记,将普通函数转换为测试。 \n assert_eq!— 一个宏,检查两个值是否相等。如果不相等,测试失败。 \n
使用命令运行测试:
\n\ncargo test\n\n如果一切正确,您将看到绿色输出:
\n\nrunning 1 test\ntest tests::test_is_even ... ok\n\ntest result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 0 filtered out\n\n恭喜,您已经编写了第一个 Rust 测试!现在让我们了解如何编写更有意义的检查。
\n\n测试中使用的主要宏
\n\n在测试中,您将经常使用三个宏。记住它们:
\n\n- \n
assert!(expression)— 检查表达式是否为真。如果为假,测试失败。 \n assert_eq!(left, right)— 检查两个值是否相等。方便比较结果。 \n assert_ne!(left, right)— 检查两个值不相等。 \n
使用所有三个宏的示例:
\n\npub fn add_two(x: i32) -> i32 {\n x + 2\n}\n\n#[cfg(test)]\nmod tests {\n use super::*;\n\n #[test]\n fn test_add_two() {\n assert!(add_two(3) == 5);\n assert_eq!(add_two(0), 2);\n assert_ne!(add_two(10), 13);\n }\n}\n\n请注意:assert! 接受一个布尔表达式,而