R包开发中:如何对返回随机值的函数进行单元测试?
针对随机舍入函数的testthat测试方案
首先明确:expect_snapshot完全不适用。因为快照测试依赖固定输出结果做对比验证,而你的函数每次调用返回结果随机变化,会导致快照次次不匹配,测试必然失败。
适合的测试方法分为以下几类:
1. 基础结构与类型验证
- 验证返回值类型:用
expect_type(round_stocho(data), "double")(或"integer",取决于函数实际返回类型) - 验证返回值长度与输入一致:
expect_length(round_stocho(data), length(data))
2. 舍入结果的合法性验证
随机舍入的核心规则是每个元素的结果只能是原数的向下取整或向上取整值,比如1.1的结果只能是1或2,1.9的结果只能是1或2:
result <- round_stocho(data) expected_bounds <- mapply(function(x) c(floor(x), ceiling(x)), data) expect_true(all(mapply(function(y, bounds) y %in% bounds, result, expected_bounds)))
3. 统计特性验证
针对随机舍入的概率逻辑,验证长期统计结果符合预期:
- 整体期望验证:输入向量1.1到1.9的总和为13.5,多次调用后的结果总和均值应接近该值:
set.seed(123) # 可选,提升测试结果稳定性 sum_samples <- replicate(1000, sum(round_stocho(data))) expect_equal(mean(sum_samples), 13.5, tolerance = 0.1) # 容差可按需调整
- 单个元素概率分布验证:比如1.5多次调用后返回1和2的次数应大致各占50%;1.3返回1的概率约70%、返回2约30%:
set.seed(123) samples_1.5 <- replicate(1000, round_stocho(1.5)) counts_1.5 <- table(samples_1.5) # 用卡方检验验证比例是否符合预期 chisq_result <- chisq.test(counts_1.5, p = c(0.5, 0.5)) expect_true(chisq_result$p.value > 0.05) # p值>0.05说明无显著差异
4. 随机性验证
验证函数确实具备随机性(极端重复情况除外):
set.seed(123) result1 <- round_stocho(data) result2 <- round_stocho(data) expect_false(identical(result1, result2)) # 注:极小概率下两次结果可能相同,可增加重复次数降低测试误判风险
内容的提问来源于stack exchange,提问作者Thaatha_Paati
相关产品推荐
相关产品推荐

