本文目录导读:

我来为你提供一个完整的Python足球比赛进球趋势分析方案,包含数据模拟和多种分析方法:
基础数据准备
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from datetime import datetime, timedelta
# 模拟一场足球比赛数据
np.random.seed(42)
# 生成比赛事件数据(分钟,事件类型,球队)
def generate_match_data():
events = []
match_duration = 90 + np.random.randint(0, 5) # 补时时间
for minute in range(1, match_duration + 1):
# 随机生成射门、进球等事件概率(随时间变化)
base_prob = 0.02 + minute * 0.0003 # 后期概率略增
# 主客队事件
for team in ['home', 'away']:
if np.random.random() < base_prob:
event_type = np.random.choice(
['shot', 'goal', 'corner', 'foul'],
p=[0.5, 0.15, 0.2, 0.15]
)
events.append({
'minute': minute,
'team': team,
'event': event_type
})
return pd.DataFrame(events)
# 生成数据
match_data = generate_match_data()
print("前5行数据:")
print(match_data.head())
进球趋势分析函数
class GoalTrendAnalyzer:
def __init__(self, match_data):
self.data = match_data
self.goals = match_data[match_data['event'] == 'goal'].copy()
def calculate_goal_timing(self):
"""计算进球时间分布"""
goal_times = self.goals['minute'].values
stats = {
'total_goals': len(goal_times),
'first_goal': goal_times.min() if len(goal_times) > 0 else None,
'last_goal': goal_times.max() if len(goal_times) > 0 else None,
'avg_goal_time': np.mean(goal_times) if len(goal_times) > 0 else None,
'std_goal_time': np.std(goal_times) if len(goal_times) > 0 else None
}
return stats
def analyze_time_segments(self, segment_min=15):
"""将比赛分成时间段分析"""
segments = []
for start in range(0, 90, segment_min):
end = min(start + segment_min, 90)
segment_goals = self.goals[
(self.goals['minute'] >= start) &
(self.goals['minute'] < end)
]
segments.append({
'segment': f'{start}-{end}分钟',
'goals': len(segment_goals),
'home_goals': len(segment_goals[segment_goals['team'] == 'home']),
'away_goals': len(segment_goals[segment_goals['team'] == 'away'])
})
return pd.DataFrame(segments)
def calculate_momentum(self, window=10):
"""计算进球动量(滑动窗口)"""
minute_range = np.arange(0, 90, 1)
momentum = []
for minute in minute_range:
# 计算前后window分钟的进球数
in_window = self.goals[
np.abs(self.goals['minute'] - minute) <= window
]
momentum.append({
'minute': minute,
'momentum_score': len(in_window),
'home_impact': len(in_window[in_window['team'] == 'home']) * 0.1,
'away_impact': len(in_window[in_window['team'] == 'away']) * 0.1
})
return pd.DataFrame(momentum)
def identify_turning_points(self):
"""识别比赛转折点"""
minutes = sorted(self.goals['minute'].values)
turning_points = []
for i in range(1, len(minutes)):
gap = minutes[i] - minutes[i-1]
if gap <= 5: # 5分钟内连续进球可能改变比赛走势
turning_points.append({
'interval': f'{minutes[i-1]}-{minutes[i]}分钟',
'gap_minutes': gap,
'intensity': 'high'
})
return turning_points
可视化分析
import matplotlib.pyplot as plt
import seaborn as sns
def visualize_trends(analyzer):
"""可视化各种趋势"""
fig, axes = plt.subplots(2, 2, figsize=(15, 10))
fig.suptitle('足球比赛进球趋势分析', fontsize=16, fontweight='bold')
# 1. 进球时间分布
ax1 = axes[0, 0]
minutes = analyzer.goals['minute']
ax1.hist(minutes, bins=15, alpha=0.7, edgecolor='black', color='skyblue')
ax1.set_xlabel('比赛分钟')
ax1.set_ylabel('进球数')
ax1.set_title('进球时间分布')
# 2. 时间段分析
ax2 = axes[0, 1]
segments = analyzer.analyze_time_segments()
x_pos = np.arange(len(segments))
width = 0.35
bars1 = ax2.bar(x_pos - width/2, segments['home_goals'], width,
label='主队', color='blue', alpha=0.7)
bars2 = ax2.bar(x_pos + width/2, segments['away_goals'], width,
label='客队', color='red', alpha=0.7)
ax2.set_xticks(x_pos)
ax2.set_xticklabels(segments['segment'])
ax2.legend()
ax2.set_ylabel('进球数')
ax2.set_title('各时间段进球分布')
# 3. 动量曲线
ax3 = axes[1, 0]
momentum = analyzer.calculate_momentum()
ax3.plot(momentum['minute'], momentum['momentum_score'],
marker='o', linewidth=2, color='green')
ax3.fill_between(momentum['minute'], momentum['momentum_score'],
alpha=0.3, color='green')
ax3.set_xlabel('比赛分钟')
ax3.set_ylabel('动量得分')
ax3.set_title('比赛动量曲线')
ax3.grid(True, alpha=0.3)
# 4. 累积进球图
ax4 = axes[1, 1]
cum_goals = analyzer.goals.sort_values('minute').copy()
cum_goals['cumulative'] = np.arange(1, len(cum_goals) + 1)
ax4.step(cum_goals['minute'], cum_goals['cumulative'],
where='post', linewidth=2, color='purple')
ax4.scatter(cum_goals['minute'], cum_goals['cumulative'],
s=50, color='purple', zorder=5)
ax4.set_xlabel('比赛分钟')
ax4.set_ylabel('累计进球数')
ax4.set_title('累积进球曲线')
ax4.grid(True, alpha=0.3)
plt.tight_layout()
plt.show()
比赛趋势评分系统
def comprehensive_trend_analysis(analyzer):
"""综合趋势分析"""
results = {}
# 基本统计
stats = analyzer.calculate_goal_timing()
results['basic_stats'] = stats
# 时间段分析
segments = analyzer.analyze_time_segments()
results['segment_analysis'] = segments
# 动量分析
momentum = analyzer.calculate_momentum()
max_momentum = momentum.loc[momentum['momentum_score'].idxmax()]
results['peak_momentum'] = {
'minute': int(max_momentum['minute']),
'score': float(max_momentum['momentum_score'])
}
# 进球密度分析
total_goals = stats['total_goals']
goals_per_half = len(analyzer.goals[analyzer.goals['minute'] <= 45])
second_half_goals = len(analyzer.goals[analyzer.goals['minute'] > 45])
results['half_analysis'] = {
'first_half_goals': goals_per_half,
'second_half_goals': second_half_goals,
'second_half_ratio': second_half_goals / max(total_goals, 1)
}
# 趋势判断
if total_goals == 0:
trend = '沉闷比赛,无进球'
elif second_half_goals > goals_per_half * 1.2:
trend = '后程发力趋势'
elif goals_per_half > second_half_goals * 1.2:
trend = '开场攻势趋势'
else:
trend = '均衡发展趋势'
results['overall_trend'] = trend
return results
# 使用示例
def main():
# 生成比赛数据
match_data = generate_match_data()
# 创建分析器
analyzer = GoalTrendAnalyzer(match_data)
# 执行分析
analysis_results = comprehensive_trend_analysis(analyzer)
# 打印结果
print("=== 比赛进球趋势分析报告 ===")
print(f"\n总进球数: {analysis_results['basic_stats']['total_goals']}")
if analysis_results['basic_stats']['total_goals'] > 0:
print(f"首球时间: 第{analysis_results['basic_stats']['first_goal']}分钟")
print(f"末球时间: 第{analysis_results['basic_stats']['last_goal']}分钟")
print(f"平均进球时间: 第{analysis_results['basic_stats']['avg_goal_time']:.1f}分钟")
print(f"\n=== 半场分析 ===")
half_data = analysis_results['half_analysis']
print(f"上半场进球: {half_data['first_half_goals']}")
print(f"下半场进球: {half_data['second_half_goals']}")
print(f"\n=== 动量峰值 ===")
peak = analysis_results['peak_momentum']
print(f"峰值时间: 第{peak['minute']}分钟")
print(f"峰值得分: {peak['score']}")
print(f"\n=== 整体趋势 ===")
print(f"趋势判断: {analysis_results['overall_trend']}")
# 可视化
visualize_trends(analyzer)
if __name__ == "__main__":
main()
进阶分析:机器学习预测
from sklearn.preprocessing import StandardScaler
from sklearn.ensemble import RandomForestRegressor
def advanced_momentum_prediction(match_data):
"""使用机器学习预测后续进球趋势"""
# 准备特征
features = []
labels = []
for minute in range(1, 80):
# 提取到当前分钟的特征
current_data = match_data[match_data['minute'] <= minute]
# 特征:累积射门、角球、犯规数
shots = len(current_data[current_data['event'] == 'shot'])
corners = len(current_data[current_data['event'] == 'corner'])
fouls = len(current_data[current_data['event'] == 'foul'])
goals = len(current_data[current_data['event'] == 'goal'])
features.append([minute, shots, corners, fouls, goals])
# 预测未来10分钟的进球数
future_data = match_data[
(match_data['minute'] > minute) &
(match_data['minute'] <= minute + 10)
]
labels.append(len(future_data[future_data['event'] == 'goal']))
# 训练模型
X = np.array(features)
y = np.array(labels)
model = RandomForestRegressor(n_estimators=100, random_state=42)
model.fit(X, y)
# 特征重要性
importance = model.feature_importances_
feature_names = ['分钟数', '射门数', '角球数', '犯规数', '进球数']
print("\n=== 特征重要性分析 ===")
for name, imp in zip(feature_names, importance):
print(f"{name}: {imp:.3f}")
return model
# 执行完整分析
match_data = generate_match_data()
analyzer = GoalTrendAnalyzer(match_data)
analysis_results = comprehensive_trend_analysis(analyzer)
visualize_trends(analyzer)
这个完整的分析系统提供了:
- 基础统计:进球时间分布、平均进球时间
- 时间段分析:15分钟为单位的进球分布
- 动量分析:滑动窗口计算比赛节奏变化
- 可视化:多种图表直观展示趋势
- 机器学习预测:预测未来进球概率
你可以根据实际需要调整参数,如:
- 修改
segment_min改变时间段粒度 - 调整动量计算的窗口大小
- 增加更多特征(传球成功率、控球率等)
这个系统可以帮助你深入分析任何比赛的进球趋势!