【问题标题】:Groupby specific column then assign new values base on conditionsGroupby 特定列然后根据条件分配新值
【发布时间】:2021-11-13 05:52:19
【问题描述】:

我有一个如下所示的数据框。

Name    M_Name       Tag        
John                  1
Dave      a           1
Mary                  1      
Sam                   1     
Chris     a           1
John                  2
Nola      f           2
Chuck                 2      
Rob                   2     
Chris     a           2
Angie                 3
Joe                   3
 :        :           : 
Tony                  n    

我需要创建一个新列 Tag_2,它基于 Tag 列和 M_Name 列。首先,我需要对 Tag 列进行分组,然后如果 M_Name 列有超过 1 个不同的字母,则整个 Tag 组将在 Tag_2 列下有一个新值“Invalid”。如果同一标签组的 M-Name 中只有 1 个字母,那么它将是“有效的”。 这是输出的样子。

Name    M_Name       Tag          Tag_2       
John                  1           Valid
Dave      a           1           Valid
Mary                  1           Valid           
Sam                   1           Valid     
Chris     a           1           Valid
John                  2          Invalid
Nola      f           2          Invalid          
Chuck                 2          Invalid      
Rob                   2          Invalid     
Chris     a           2          Invalid
Angie                 3           Valid
Joe                   3           Valid
 :        :           : 
Tony                  n           Valid    

标签 2 组为“无效”,因为 M_Name 行中标签 2 组有超过 1 个不同的字母 (f & a)。

我正在考虑使用 groupby 来解决此任务,但我不知道如何添加这样的条件。 df.groupby('Tag')['M_Name'] 我想知道我是否在使用 groupby 的正确道路上,还是我应该考虑任何更好的方法?

谢谢!

【问题讨论】:

    标签: python pandas pandas-groupby


    【解决方案1】:

    我确信有更好的方法,但这里有一个解决方案:

    def validate(s):
        return "Invalid" if len(set(s)) > 2 else "Valid"
    
    
    mapping = df.groupby("Tag")["M_Name"].apply(validate)
    df["Tag_2"] = df.loc[:, "Tag"].replace(mapping)
    

    输出:

         Name M_Name  Tag    Tag_2
    0    John           1    Valid
    1    Dave      a    1    Valid
    2    Mary           1    Valid
    3     Sam           1    Valid
    4   Chris      a    1    Valid
    5    John           2  Invalid
    6    Nola      f    2  Invalid
    7   Chuck           2  Invalid
    8     Rob           2  Invalid
    9   Chris      a    2  Invalid
    10  Angie           3    Valid
    11    Joe           3    Valid
    

    【讨论】:

    • 它有效,但我想知道set() 在上面的代码中做了什么?
    • 集合长度是序列中唯一元素的个数。
    【解决方案2】:

    首先,我们group(),然后我们transform()M_Name 列,其中lambda 中我们过滤掉空值x[x.ne('')],然后使用value_counts() 来获取元素频率,并根据元素的数量,我们确定有效性:

    df = pd.DataFrame(
        {'Name': ['John', 'Dave', 'Mary', 'Sam', 'Chris', 'John', 'Nola', 'Chuck', 'Rob', 'Chris', 'Angie', 'Joe'],
         'M_Name': ['', 'a', '', '', 'a', '', 'f', '', '', 'a', '', ''], 'Tag': [1, 1, 1, 1, 1, 2, 2, 2, 2, 2, 3, 3]})
    
    df['Tag2'] = df.groupby('Tag').M_Name.transform(
        lambda x: 'Invalid' if x[x.ne('')].value_counts().shape[0] > 1 else 'Valid')
    print(df)
    

    输出:

         Name M_Name  Tag     Tag2
    0    John           1    Valid
    1    Dave      a    1    Valid
    2    Mary           1    Valid
    3     Sam           1    Valid
    4   Chris      a    1    Valid
    5    John           2  Invalid
    6    Nola      f    2  Invalid
    7   Chuck           2  Invalid
    8     Rob           2  Invalid
    9   Chris      a    2  Invalid
    10  Angie           3    Valid
    11    Joe           3    Valid
    

    【讨论】:

    • 这是一个很好的方法。非常感谢分享这个解决方案!
    猜你喜欢
    • 1970-01-01
    • 2020-09-17
    • 1970-01-01
    • 2021-06-11
    • 1970-01-01
    • 2020-06-04
    • 2018-04-30
    • 1970-01-01
    • 2019-04-06
    相关资源
    最近更新 更多