【问题标题】:Python Pandas groupby, rank, then assign value based on custom rankPython Pandas groupby,排名,然后根据自定义排名分配值
【发布时间】:2015-09-05 09:38:59
【问题描述】:

问题设置

熊猫数据框

df = pd.DataFrame({'Group': ['A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A'], 'Subgroup': ['Group 1', 'Group 1', 'Group 1', 'Group 1', 'Group 1', 'Group 1', 'Group 2', 'Group 2', 'Group 2'], 'Keyword': ['kw 1', 'kw 1', 'kw 1', 'kw 2', '+kw +2', 'kw 2', 'kw 3', 'kw 3', 'kw 3'], 'Normalized': ['kw 1', 'kw 1', 'kw 1', 'kw 2', 'kw 2', 'kw 2', 'kw 3', 'kw 3', 'kw 3'], 'Criterion Type': ['Exact', 'Phrase', 'Broad', 'Phrase', 'Broadified', 'Exact', 'Broad', 'Exact', 'Phrase'], 'Max CPC': [1.62, 1.73, 0.87, 1.70, 0.85, 1.60, 0.99, 1.58, 1.68], 'CPC Rank': [2, 1, 3, 1, 3, 2, 3, 2, 1], 'Type Rank': [1, 2, 3, 2, 3, 1, 3, 1, 2]})

这样可以将列放在正确的位置:

df = df[['Group', 'Subgroup', 'Keyword', 'Normalized', 'Criterion Type', 'Max CPC', 'CPC Rank', 'Type Rank']]

目标

groupby['Group', 'Subgroup', 'Normalized'],然后是rankMax CPCs。接下来,我想将与CPC Rank 关联的Max CPC 映射到基于Criterion Type 和我自己的自定义排名确定的Type Rank{'Exact':1, 'Phrase':2, 'Broadified':3, 'Broad':4}

结果将是New CPC 列及其相应的Max CPC

【问题讨论】:

    标签: python dictionary pandas dataframe ranking


    【解决方案1】:

    我已经对每个组内的值进行了排序,并使用索引分配了排序后的值。 这是你想要的吗?

    df['new CPC'] = -1
    parts = []
    grouped = df.groupby(['Group', 'Subgroup', 'Normalized'])
    for name, group in grouped:
        type_rank_index = group.sort(columns='Type Rank').index
        cpc_rank_index = group.sort(columns='CPC Rank').index
        group.loc[type_rank_index, 'new CPC'] = group.loc[cpc_rank_index, 'Max CPC']
        parts.append(group)
    
    result = pd.concat(parts)
    

    【讨论】:

    • 当我尝试你的例子时,最后,Max CPC 等于 new CPC 这不应该发生,因为我试图根据他们的 Max CPCs 和关键字重新分配 Max CPCs Criterion Type.
    • @Jarad 抱歉,我无法理解您的要求。请再解释清楚,我会在上面更改我的答案。
    【解决方案2】:
    import pandas as pd
    import numpy as np
    
    df = pd.DataFrame({'Group': ['A', 'A', 'A', 'A', 'A', 'A', 'A', 'A', 'A'], 'Subgroup': ['Group 1', 'Group 1', 'Group 1', 'Group 1', 'Group 1', 'Group 1', 'Group 2', 'Group 2', 'Group 2'], 'Keyword': ['kw 1', 'kw 1', 'kw 1', 'kw 2', '+kw +2', 'kw 2', 'kw 3', 'kw 3', 'kw 3'], 'Normalized': ['kw 1', 'kw 1', 'kw 1', 'kw 2', 'kw 2', 'kw 2', 'kw 3', 'kw 3', 'kw 3'], 'Criterion Type': ['Exact', 'Phrase', 'Broad', 'Phrase', 'Broadified', 'Exact', 'Broad', 'Exact', 'Phrase'], 'Max CPC': [1.62, 1.73, 0.87, 1.70, 0.85, 1.60, 0.99, 1.58, 1.68], 'CPC Rank': [2, 1, 3, 1, 3, 2, 3, 2, 1], 'Type Rank': [1, 2, 3, 2, 3, 1, 3, 1, 2]})
    df = df[['Group', 'Subgroup', 'Keyword', 'Normalized', 'Criterion Type', 'Max CPC', 'CPC Rank', 'Type Rank']]
    
    #Sort by custom priority based on their Criterion Type
    df = df.sort(['Group', 'Subgroup', 'Normalized', 'Type Rank'])
    #Reset index and drop old one
    df = df.reset_index(drop=True)
    print(df)
    #Create df1 which is a Series of the Max CPC column in its correctly ranked order
    df1 = df.sort(['Group', 'Subgroup', 'Normalized', 'CPC Rank'])['Max CPC']
    #Reset index and drop old one
    df1 = df1.reset_index(drop=True)
    print(df1)
    
    #Add the df1 Series to df and name the column New CPC
    df['New CPC'] = df1
    
    print(df)
    

    这是迄今为止解决此问题最有效的方法。困难的部分是意识到我可以通过Type Rank sort df 所以Criterion Type 行是按他们的等级排序的。这意味着我希望最高的Max CPC 应用于第一个,第二个最高的Max CPC 应用于第二个,依此类推。

    然后我所要做的就是创建一个Max CPC SeriesCPC Rank 排序。

    最后,将此Series 添加到现有的df

    【讨论】:

      【解决方案3】:

      试试这个

      def group_rank(df):
          # first of all you've to rank according to `Max CPC`
          df['CPC Rank'] = df['Max CPC'].rank(ascending = False)
          # create the mapping
          mapping = pd.Series(data=df['Max CPC'].values , index= df['CPC Rank'].values)
          # create new column according to your ranking
          df['New CPC'] = df['Type Rank'].map(mapping)
          return df
      
      df.groupby(['Group', 'Subgroup', 'Normalized']).apply(group_rank)
      

      【讨论】:

      • mapping 包含具有非唯一值的索引。在定义New CPC 时,map(mapping) 似乎会导致pandas.core.index.InvalidIndexError: Reindexing only valid with uniquely valued Index objects 错误。您的函数在我的示例 df 中有效,但我在较大的数据集上得到 InvalidIndexError。另外,当我不在函数中定义mapping,然后执行df['New CPC'] = df['Type Rank'].map(mapping),它也会引发错误。这种类型的映射只在函数中起作用吗?无论哪种方式,我都需要研究这个。感谢您的概念。
      • 这意味着每个组都有重复的 Type rank 值,对吗?如果是这样,在这种情况下你应该如何映射你的价值观?
      • 是的,这是可能的(罕见/不常见,但仍有可能)。 Type Rank 数字是根据我自己的自定义排名得出的:{'Exact':1, 'Phrase':2, 'Broadified':3, 'Broad':4}。此自定义排名基于Criterion Type,同一组中的两行可能是Broadified,它映射到3 作为Type Rank。在这少数情况下,对它们进行排名的最佳方法是基于 Keyword 列中的 + 符号 - + 符号越多,排名越低,+ 符号越少,排名越高。例如:+kw +2 = Type Rank 2, +kw 2, = Type Rank 3。
      猜你喜欢
      • 2023-03-08
      • 2018-11-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-07-21
      • 1970-01-01
      • 1970-01-01
      • 2023-02-02
      相关资源
      最近更新 更多