本文目录导读:

数据准备
1 需要的字段
| 字段 | 说明 |
|---|---|
| player_id | 球员唯一标识 |
| player_name | 球员姓名 |
| club | 俱乐部 |
| country | 国家队 |
| match_date | 比赛日期 |
| competition | 赛事类型(联赛/杯赛/国家队) |
| minutes_played | 出场分钟 |
| travel_distance_km | 飞行距离(可选) |
| days_rest | 距上场比赛天数 |
| rating | 赛后评分 |
| goals/assists | 进球/助攻 |
| injury_flag | 是否受伤 |
2 数据来源建议
- Transfermarkt:伤病、出场记录
- FBref / Understat:进阶数据(xG、xA、评分)
- Football-Lineups:首发阵容
- API-Football:赛程与国家队征召
分析框架(Python 脚本)
import pandas as pd
import numpy as np
from scipy import stats
import matplotlib.pyplot as plt
import seaborn as sns
# ========== 1. 读取数据 ==========
df = pd.read_csv("player_matches.csv", parse_dates=["match_date"])
# ========== 2. 标记国家队比赛周 ==========
# FIFA国际比赛日通常为3月、6月、9月、10月、11月
fifa_windows = [
("2024-03-18", "2024-03-26"),
("2024-06-03", "2024-06-11"),
("2024-09-02", "2024-09-10"),
("2024-10-07", "2024-10-15"),
("2024-11-11", "2024-11-19"),
]
def is_fifa_window(date):
for start, end in fifa_windows:
if pd.Timestamp(start) <= date <= pd.Timestamp(end):
return True
return False
df["is_fifa_window"] = df["match_date"].apply(is_fifa_window)
# ========== 3. 标记"后遗症期" ==========
# 定义:国家队比赛周结束后 0-14 天内的俱乐部比赛
def days_since_fifa(date):
for start, end in fifa_windows:
end_dt = pd.Timestamp(end)
if date > end_dt:
delta = (date - end_dt).days
if delta <= 14:
return delta
return np.nan
df["days_post_fifa"] = df["match_date"].apply(days_since_fifa)
df["post_fifa"] = df["days_post_fifa"].notna()
# ========== 4. 分组对比 ==========
# 只保留俱乐部比赛
club_df = df[df["competition"] != "国家队"].copy()
# 分组:后遗症期 vs 正常期
group_post = club_df[club_df["post_fifa"]]
group_normal = club_df[~club_df["post_fifa"]]
# ========== 5. 核心指标对比 ==========
metrics = ["rating", "goals", "assists", "minutes_played"]
results = []
for m in metrics:
t_stat, p_val = stats.ttest_ind(
group_post[m].dropna(), group_normal[m].dropna(), equal_var=False
)
results.append({
"指标": m,
"后遗症期均值": group_post[m].mean(),
"正常期均值": group_normal[m].mean(),
"差异": group_post[m].mean() - group_normal[m].mean(),
"p值": p_val,
"显著性": "***" if p_val < 0.01 else "**" if p_val < 0.05 else "*" if p_val < 0.1 else "ns"
})
result_df = pd.DataFrame(results)
print(result_df)
# ========== 6. 伤病风险分析 ==========
injury_rate_post = group_post["injury_flag"].mean()
injury_rate_normal = group_normal["injury_flag"].mean()
print(f"\n后遗症期伤病率: {injury_rate_post:.2%}")
print(f"正常期伤病率: {injury_rate_normal:.2%}")
print(f"相对风险 (RR): {injury_rate_post / injury_rate_normal:.2f}")
# ========== 7. 按飞行距离分层 ==========
if "travel_distance_km" in club_df.columns:
club_df["travel_bin"] = pd.cut(
club_df["travel_distance_km"],
bins=[0, 2000, 5000, 10000, 20000],
labels=["短途", "中途", "长途", "超长途"]
)
travel_analysis = club_df.groupby("travel_bin")["rating"].agg(["mean", "count"])
print("\n按飞行距离的评分:")
print(travel_analysis)
# ========== 8. 可视化 ==========
fig, axes = plt.subplots(1, 3, figsize=(18, 5))
# 评分分布
sns.boxplot(data=club_df, x="post_fifa", y="rating", ax=axes[0])
axes[0].set_title("后遗症期 vs 正常期评分分布")
axes[0].set_xticklabels(["正常期", "后遗症期"])
# 按天数衰减
daily = club_df[club_df["post_fifa"]].groupby("days_post_fifa")["rating"].mean()
axes[1].plot(daily.index, daily.values, marker="o")
axes[1].set_title("国家队比赛后天数 vs 评分")
axes[1].set_xlabel("距国家队比赛结束天数")
axes[1].set_ylabel("平均评分")
# 伤病率对比
axes[2].bar(["正常期", "后遗症期"], [injury_rate_normal, injury_rate_post], color=["steelblue", "crimson"])
axes[2].set_title("伤病率对比")
axes[2].set_ylabel("伤病率")
plt.tight_layout()
plt.savefig("fifa_virus_analysis.png", dpi=150)
plt.show()
进阶分析维度
1 球员分层
# 按年龄分层
club_df["age_group"] = pd.cut(club_df["age"], bins=[0, 23, 28, 32, 40],
labels=["U23", "24-28", "29-32", "33+"])
age_analysis = club_df.groupby(["age_group", "post_fifa"])["rating"].mean().unstack()
print(age_analysis)
# 按出场时间分层
club_df["minutes_load"] = pd.cut(club_df["minutes_played"],
bins=[0, 45, 90, 180],
labels=["低", "中", "高"])
2 俱乐部影响
# 哪些俱乐部受影响最大
club_impact = club_df.groupby(["club", "post_fifa"])["rating"].mean().unstack()
club_impact["diff"] = club_impact[True] - club_impact[False]
club_impact = club_impact.sort_values("diff")
print(club_impact.head(10)) # 受影响最大的
3 因果推断(DID 双重差分)
# 如果有对照组(无国脚的俱乐部),可用DID
# treated: 有国脚回归的球员
# control: 无国脚的球员
# time: 后遗症期 vs 正常期
import statsmodels.formula.api as smf
model = smf.ols("rating ~ post_fifa * treated + C(player_id) + C(match_date)",
data=club_df).fit()
print(model.summary())
结论输出模板
def generate_report(result_df, injury_rate_post, injury_rate_normal):
report = f"""
╔══════════════════════════════════════════════╗
║ 国家队比赛日后遗症分析报告 ║
╠══════════════════════════════════════════════╣
║ 1. 评分变化: {result_df.loc[0, '差异']:+.3f} (p={result_df.loc[0, 'p值']:.3f})
║ 2. 进球变化: {result_df.loc[1, '差异']:+.3f}
║ 3. 伤病率: {injury_rate_normal:.1%} → {injury_rate_post:.1%}
║ 4. 相对风险: {injury_rate_post/injury_rate_normal:.2f}x
╚══════════════════════════════════════════════╝
"""
return report
print(generate_report(result_df, injury_rate_post, injury_rate_normal))
实用建议
| 角色 | 行动 |
|---|---|
| 教练 | 后遗症期前2场考虑轮换,尤其是长途飞行球员 |
| 体能教练 | 监测CK值、睡眠质量,制定恢复计划 |
| 分析师 | 用xG链、跑动数据补充评分,避免单一指标偏差 |
| 投注者 | 关注"国脚大户"球队在后遗症期的让球盘口 |
| FM/游戏玩家 | 国际比赛日后避免让核心球员首发 |
注意事项
- 样本量:单个国际比赛日窗口样本有限,建议跨赛季合并
- 混杂因素:对手强度、主客场、赛程密度需控制
- 选择偏差:能踢国家队的球员本身实力更强,需用DID或匹配法
- 定义敏感:”后遗症期“天数(7天/14天)会影响结果,建议做敏感性分析
- 位置差异:门将受影响小,边锋/中场受影响大
如果你有具体的数据集(CSV/Excel),我可以帮你直接跑这个脚本并解读结果,也可以针对某个联赛(英超/中超)或某支球队做定制分析,需要我展开哪一部分?
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
足球直播
足球直播
足球直播
篮球直播
篮球直播
篮球直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
亚冠直播
亚冠直播
亚冠直播
欧冠直播
欧冠直播
欧冠直播
英超直播
英超直播
英超直播
西甲直播
西甲直播
西甲直播
中超直播
中超直播
中超直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
曼联直播
曼联直播
曼联直播
日职联直播
日职联直播
日职联直播
澳超直播
澳超直播
澳超直播
阿森纳直播
阿森纳直播
阿森纳直播
足球直播
足球直播
足球直播
NBA直播
NBA直播
NBA直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
欧冠直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
篮球直播
篮球直播
篮球直播
篮球直播
篮球直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播
中超直播