英超足球比分贝叶斯泊松模型JAGS代码报错排查求助
英超比分预测贝叶斯Poisson模型JAGS报错解决
错误根源分析
第一次报错(变量未找到)
- 循环内为每场比赛的
h_att[i]、a_def[i]定义先验是完全错误的逻辑:每支球队的攻防能力是全局唯一参数,并非每场比赛都有独立参数。 - 数据集里的
h_att列是球队名称字符串,你试图监控att_Crystal_Palace这类变量,但模型里根本没定义这些变量——循环内仅定义了h_att[i]这类临时变量,JAGS自然找不到对应节点。
第二次报错(节点重复定义)
- 单独定义每支球队的攻防参数时,要么是代码复制粘贴过程中重复定义了同一变量(比如多次写了
def_Liverpool),要么是循环内的变量引用方式错误,导致JAGS判定你在重复创建同一节点。
解决方法
核心思路是用数字索引映射球队,将攻防参数定义为全局向量,通过索引关联每场比赛的对应球队参数:
1. 预处理数据集(R代码)
把球队名称转换为数字ID,便于JAGS通过索引调用参数:
# 提取所有唯一球队 teams = unique(c(test_set$HomeTeam, test_set$AwayTeam)) # 为球队分配1-20的数字ID test_set$home_id = match(test_set$HomeTeam, teams) test_set$away_id = match(test_set$AwayTeam, teams) # 整理JAGS输入数据 data_jags = list( FTHG = test_set$FTHG, FTAG = test_set$FTAG, home_id = test_set$home_id, away_id = test_set$away_id, n_teams = length(teams), n_games = nrow(test_set) )
2. 正确的JAGS模型代码
bayes_mod_string = "model{ # 全局截距与主场优势参数先验 mu ~ dnorm(0, 1/1e6) hfa ~ dnorm(0, 1/1e6) # 每支球队的攻防能力全局先验(向量形式) for (t in 1:n_teams){ att[t] ~ dnorm(0, 1/1e6) def[t] ~ dnorm(0, 1/1e6) } # 每场比赛的Poisson似然计算 for (i in 1:n_games){ FTHG[i] ~ dpois(lam_h[i]) log(lam_h[i]) = mu + hfa + att[home_id[i]] - def[away_id[i]] FTAG[i] ~ dpois(lam_a[i]) log(lam_a[i]) = mu + att[away_id[i]] - def[home_id[i]] } }"
3. 运行模型(R代码)
# 初始化模型 bayes_mod = jags.model(textConnection(bayes_mod_string), data = data_jags, n.chains = 3) # 烧录迭代 update(bayes_mod, 1000) # 采样参数 params = c("mu", "hfa", "att", "def") bayes_mod_sim = coda.samples(model = bayes_mod, variable.names = params, n.iter = 1000) bayes_mod_csim = as.mcmc(do.call(rbind, bayes_mod_sim))
内容的提问来源于stack exchange,提问作者Juan
相关产品推荐
相关产品推荐

