我想模拟不同的扑克手。通过痛苦的反复试验,我得到了等级、花色、套牌和一个抽取任何给定数量的牌的功能,如下所示:
suits <- c("spd","hrt","dimd","clbs")
ranks <- c(1:10,"J","Q","K")
deck <- as.matrix(expand.grid('rank' = ranks, 'suit' = suits))
draw <- function (n) deck[sample(nrow(deck), n), ]
draw(5) # Drawing 5 cards from the deck...
输出:
rank suit
[1,] "4" "dimd"
[2,] "6" "dimd"
[3,] "8" "spd"
[4,] "K" "hrt"
[5,] "8" "clbs"
现在我想通过模拟找出获得不同手牌的概率。我确实想出了一些可能的循环counter for the number of successes
但我被卡住了。
下面是一个示例...让我试着弄清楚我在 1000 次模拟中得到了多少完整的房子。由于满屋被定义为"三张一个等级的匹配牌和两张另一个等级的匹配牌",我认为该函数的关键部分是在利用 R 函数unique()==2
的 if
语句中有一个布尔值,这意味着 2 个唯一的等级 - 发了 5 张牌, 2个独特的等级可能是一个完整的房子(另一种可能性是任何其他等级的四个
iterations <- 1000
counter <- 0
for (i in iterations){
s <- draw(5)
if(length(unique(s[,1])) == 2) counter <- counter + 1
}
counter
输出:[1] 0
我已经尝试了其他多种方法,包括成功案例的counter[i] <- 1
,以及最后运行sum(counter)
的想法,但所有这些都没有让循环工作。
在你的代码中,你有:
for(i in 1000) {
print(i)
} # 1000
它只会打印一次,因为i
会迭代一次作为1000
。
这是使用 rle
的替代方法。
iterations <- 10000
draws <- list()
for (i in 1:iterations){
s <- draw(5)
draws[[i]] <- all(rle(sort(s[,1]))$lengths %in% c(2,3))
if(draws[[i]]) {
print(s)
}
}
summary(unlist(draws))
使用如下数据框,它似乎会产生您正在寻找的结果:
suits <- c("spd","hrt","dimd","clbs")
ranks <- c(1:10,"J","Q","K")
deck <- as.data.frame(expand.grid('rank' = ranks, 'suit' = suits))
draw <- function (n) deck[sample(nrow(deck), n), ]
counter <- 0;
for (i in 1:1000) {
df <- draw(5);
counter <- counter + (length(unique(df$rank)) == 2)
}
counter
[1] 156
suits <- c("spd","hrt","dimd","clbs")
ranks <- c(1:10,"J","Q","K")
deck <- as.data.frame(expand.grid('rank' = ranks, 'suit' = suits))
draw <- function (n) deck[sample(nrow(deck), n), ]
iterations <- 1000
counter <- 0
for (i in 1:iterations) {
hand <- draw(5)
rank_table <- table(hand[, 1])
if (length(names(rank_table)) == 2 & min(rank_table) > 1) counter <- counter + 1
# could have four of a rank, one of another;
# need to ensure two of a rank, three of another
}
counter
[1] 1
这个结果与预期的 http://www.math.hawaii.edu/~ramsey/Probability/PokerHands.html 相差不远