问题:您真的可以根据过滤器内部的绘制可靠地执行过滤吗,或者它注定会失败?
目标:在 中dplyr::filter()
,如果随机抽签失败,则删除 A 类(versicolor)行,如果抽签通过,则删除 B 类(virginica)行。应始终以 5 行 setosa 数据随机行和 1 行 virginica(1/8 机会)或 versicolor(7/8 机会)随机行结束。
试图:
as_tibble(iris) %>%
group_by(Species) %>%
mutate(draw = case_when(
Species == "setosa" ~ 5,
Species == "versicolor" ~ 1,
Species == "virginica" ~ 1
)) %>%
slice(sample(n(),draw[1])) %>%
filter(
if(round(runif(1),3) <= 1/8){ Species != "versicolor" }
else { Species != "virginica" }
)
问题:虽然这通常只返回一个或另一个,但偶尔我会同时返回两个或两个都不返回。 出于好奇,我发现有 11% 的时间我同时返回两个,有 11% 的时间我一个都不返回,而只有 78% 的时间只返回一个(这是正确的)。
我理解一个解决方案是在切片之后结束管道,然后在语句内进行绘制if()
:
data <- as_tibble(iris) %>%
group_by(Species) %>%
mutate(draw = case_when(
Species == "setosa" ~ 5,
Species == "versicolor" ~ 1,
Species == "virginica" ~ 1
)) %>%
slice(sample(n(),draw[1]))
if(round(runif(1),3) <= 1/8){
data %>%
filter(Species != "versicolor")
}
else {
data %>%
filter(Species != "virginica")
}
但是,自从我意识到可以在过滤器内部进行绘制后,我便很有兴趣了解它是否实用。
你为什么不事先计算一下概率呢?
它看上去比
if ... else
最后更干净。有时它不打印任何内容或不打印任何内容,是因为您提取的不是 1 个随机数,而是 3 个!每个组一个。
filter
在您的代码中被应用于分组data.frame
,因此您会得到每个组一个随机数。尝试运行此代码。您将看到它将打印 3 个数字。
ungroup
因此,您只需在之前添加以下内容即可更正代码filter
: