0

我有一个大型数据框,用于整理一堆篮球数据(截图如下)。Opp Lineup 右侧的每一列都是一个虚拟变量,表示该球员(列名表示)是否在当前阵容中(列名的最后一部分是队名,需要与对手列进行比较确保在不同球队中拥有相同号码和姓名的两名球员不会搞砸)。我知道迭代熊猫数据框的几种方法(iterrows、itertuples、iteritems),但我不知道完成我需要的方法,即每列中的每一行:

  1. 将球队 (columnname.split()[2:]) 与对手列进行比较(LSU 球员除外)
  2. 查看名称 (columnname.split()[:2]) 是否在 Opp Lineup 中,或者对于 LSU 玩家,在 lineup 中
  3. 如果满足上述条件,则将该值替换为 1,否则将其保留为 0

在此处输入图像描述

循环遍历数据框并完成此任务的最佳方法是什么?在这种情况下,速度并不重要。我了解所涉及的所有逻辑,除了我对 pandas 不够熟悉,不知道如何遍历它,并且尝试了我在 Google 上看到的各种方法都不起作用。

4

2 回答 2

1

考虑一个重塑/枢轴解决方案,因为您的数据是宽格式的,但您需要逐行比较长格式的值。因此,首先融合您的数据,使所有列标题成为实际列'Player',并将其对应的值转换为'IsInLineup'. 运行虚拟值的条件比较,然后跨列标题返回原始结构与玩家。当然,我没有实际数据来完全测试这个例子。

# MELT 
reshapedf = pd.melt(df, id_vars=['Opponent', 'Lineup', 'Minutes', 'Plus Minus', 
                                 'Plus Minus Per Minute', 'Opp Lineup'], 
                    var_name='Player', value_name='IsInLineup')

# APPLY FUNCTION (SPLITTING VALUE AND THEN JOINING FOR SUBSET STRING)
reshapedf['IsInLineup'] = reshapedf.apply(lambda row: (' '.join(row['Player'].split(' ')[:2]) in row['Opp Lineup'] and
                                                       ' '.join(row['Player'].split(' ')[2:]) in row['Opponent'])*1, axis=1)

# PIVOT (UNMELT)
df2 = reshapedf.pivot_table(index=['Opponent', 'Lineup', 'Minutes', 'Plus Minus', 
                                   'Plus Minus Per Minute', 'Opp Lineup'], columns='Player').reset_index()
df2.columns = df2.columns.droplevel(0).rename(None)
df2.columns = df.columns

如果上面的 lambda 函数看起来有点复杂,试试等效的 apply defined function():

# APPLY FUNCTION (SPLITTING VALUE AND THEN JOINING FOR SUBSET STRING)
def f(row):
    if (' '.join(row['Player'].split(' ')[:2]) in row['Opp Lineup'] and \
        ' '.join(row['Player'].split(' ')[2:]) in row['Opponent']):
        return 1
    else:
        return 0

reshapedf['IsInLineup'] = reshapedf.apply(f,axis=1)
于 2016-02-16T23:32:41.113 回答
0

我最终使用了解决方法。我使用 df.iterrows 进行迭代,并为每个迭代创建一个列表,在其中检查我想要的值,然后将 0 或 1 附加到临时列表中。然后我只是将它插入到数据框中。可能不是最有效的记忆方式,但它有效。

于 2016-02-25T23:22:24.813 回答