足球数据分析绘图遇TypeError:字符串索引必须为整数而非字符串
足球数据分析绘图报错:
string indices must be integers, not 'str' 我正在进行足球数据分析,已基于两列条件生成子DataFrame,尝试在球场上绘制事件时触发错误:string indices must be integers, not 'str'。
所用DataFrame
| typeId | outcome | x | y | endX | endY | |
|---|---|---|---|---|---|---|
| 0 | 49 | 1 | 36.7 | 59.6 | 0.0 | 0.0 |
| 1 | 1 | 1 | 36.7 | 59.6 | 41.4 | 65.1 |
| 2 | 1 | 1 | 41.4 | 65.1 | 26.8 | 70.4 |
| 3 | 1 | 1 | 26.8 | 70.4 | 28.7 | 40.3 |
| 4 | 1 | 1 | 28.6 | 37.6 | 39.5 | 29.3 |
| 5 | 1 | 1 | 39.5 | 29.3 | 30.8 | 38.8 |
| 6 | 1 | 1 | 30.8 | 38.8 | 20.7 | 39.2 |
| 7 | 1 | 1 | 20.7 | 39.2 | 21.2 | 85.5 |
| 8 | 1 | 1 | 21.2 | 85.5 | 32.3 | 96.0 |
| 9 | 1 | 1 | 45.2 | 96.2 | 71.5 | 93.5 |
| 10 | 1 | 1 | 84.5 | 94.5 | 90.6 | 80.3 |
| 11 | 1 | 1 | 90.6 | 80.3 | 94.2 | 95.2 |
| 12 | 1 | 1 | 96.0 | 96.5 | 91.0 | 95.9 |
| 13 | 1 | 1 | 87.6 | 96.7 | 72.5 | 78.0 |
| 14 | 1 | 1 | 72.5 | 78.0 | 57.8 | 78.4 |
| 15 | 1 | 1 | 57.8 | 78.4 | 72.0 | 89.7 |
| 16 | 1 | 1 | 74.5 | 79.4 | 97.9 | 80.5 |
| 17 | 1 | 1 | 98.6 | 80.3 | 87.9 | 36.0 |
| 18 | 16 | 1 | 89.9 | 37.1 | 0.0 | 0.0 |
执行代码
for event in df1: if event['typeId'] == 1: pitch.arrows(df1.x, df1.y, df1.endX, df1.endY, lw=1.0, color='green', zorder=1, ax=axs[0,0]) elif event['type'] == 16: pitch.scatter(event.x, event.y, s=450, edgecolors='#b94b75', linewidths=0.6, c='white', marker='football', ax=axs[0,0])
报错信息
TypeError Traceback (most recent call last) Cell In[21], line 20 18 # Plot the events 19 for event in df1: ---> 20 if event['typeId'] == 1: 21 pitch.arrows(df1.x, df1.y, df1.endX, df1.endY, lw=1.0, color='green', zorder=1, ax=axs[0,0]) 22 elif event['type'] == 16: TypeError: string indices must be integers, not 'str'
问题原因与解决方法
核心问题
直接for event in df1遍历的是DataFrame的列名(字符串类型),而非每一行数据。所以event['typeId']本质是对字符串用字符串索引,自然触发类型错误。
方法1:用iterrows()遍历行
这是最直接的修正方式,遍历每一行的索引和数据:
for idx, event in df1.iterrows(): if event['typeId'] == 1: # 注意:这里要传单条数据的x/y,而非整个列 pitch.arrows(event.x, event.y, event.endX, event.endY, lw=1.0, color='green', zorder=1, ax=axs[0,0]) elif event['typeId'] == 16: # 原代码里的type是笔误,应该是typeId pitch.scatter(event.x, event.y, s=450, edgecolors='#b94b75', linewidths=0.6, c='white', marker='football', ax=axs[0,0])
方法2:向量式操作(更高效)
Pandas不推荐逐行循环,建议直接筛选数据后批量绘图,效率更高:
# 筛选typeId=1的行,批量绘制箭头 passes = df1[df1['typeId'] == 1] pitch.arrows(passes.x, passes.y, passes.endX, passes.endY, lw=1.0, color='green', zorder=1, ax=axs[0,0]) # 筛选typeId=16的行,批量绘制散点 shots = df1[df1['typeId'] == 16] pitch.scatter(shots.x, shots.y, s=450, edgecolors='#b94b75', linewidths=0.6, c='white', marker='football', ax=axs[0,0])
额外修正点
原代码中elif event['type'] == 16是笔误,DataFrame的列名是typeId,需改为event['typeId']。
内容的提问来源于stack exchange,提问作者WilliamAshoti
相关产品推荐
相关产品推荐

