【问题标题】:Why don't pipe() or apply() work properly on this pandas groupby?为什么 pipe() 或 apply() 在这个 pandas groupby 上不能正常工作?
【发布时间】:2018-12-26 21:48:36
【问题描述】:

我有带有 col1, col2, col3 列的 DataFrame。我想为col1 中的每个组分别创建另一个col4 包含col2[n+3]/col2-1

+-----+------+-----+
|col1 | col2 | col3|
+-----+------+-----+    
|  A  |  2   |  4  |
+-----+------+-----+    
|  A  |  4   |  5  | 
+-----+------+-----+    
|  A  |  7   |  7  | 
+-----+------+-----+    
|  A  |  3   |  8  | 
+-----+------+-----+    
|  A  |  7   |  3  | 
+-----+------+-----+    
|  B  |  8   |  9  |
+-----+------+-----+    
|  B  |  10  |  10 | 
+-----+------+-----+    
|  B  |  8   |  9  |
+-----+------+-----+    
|  B  |  20  |  15 |
+-----+------+-----+

输出应该是:

   +-----+------+-----+-----+
   |col1 | col2 | col3| col4|
   +-----+------+-----+-----+    
   | A   |    2 |   4 |  0.5|  # (3/2-1)
   +-----+------+-----+-----+    
   | A   |    4 |   5 | 0.75|  # (7/4-1)
   +-----+------+-----+-----+    
   | A   |    7 |   7 |  NA |
   +-----+------+-----+-----+    
   | A   |    3 |   8 |  NA |
   +-----+------+-----+-----+    
   | A   |    7 |   3 |  NA |
   +-----+------+-----+-----+    
   | B   |    8 |   9 | 1.5 |
   +-----+------+-----+-----+    
   | B   |   10 |  10 |  NA |
   +-----+------+-----+-----+    
   | B   |    8 |  9  |  NA |
   +-----+------+-----+-----+    
   | B   |   20 |  15 |  NA |
   +-----+------+-----+-----+

我的代码是

df['col4']= df.groupby('col1').apply(lambda x: x['col2'].shift(-3)/x['col2']-1)

导致col4 的所有条目均为“NA”。

我也试过了:

df['col4']= df.groupby('col1').pipe(lambda x: x['col2'].shift(-3)/x['col2']-1)

忽略组“A”和“B”并导致:

 +-----+------+-----+-------+  
 |col1 | col2 | col3| col4  |
 +-----+------+-----+-------+      
 | A   |  2   |  4  | 0.5   |
 +-----+------+-----+-------+      
 | A   |  4   |  5  | 0.75  |
 +-----+------+-----+-------+      
 | A   |  7   |  7  | 0.1428|
 +-----+------+-----+-------+          
 | A   |  3   |  8  | 2.33  |
 +-----+------+-----+-------+          
 | A   |  7   |  3  | 0.1428|
 +-----+------+-----+-------+          
 | B   |  8   |  9  | 1.5   |
 +-----+------+-----+-------+          
 | B   | 10   | 10  | NA    |
 +-----+------+-----+-------+          
 | B   |  8   |  9  | NA    |
 +-----+------+-----+-------+          
 | B   | 20   | 15  | NA    |
 +-----+------+-----+-------+      

有人知道如何完成这项任务或修复我的代码吗?

【问题讨论】:

标签: python dataframe pipe apply pandas-groupby


【解决方案1】:

IIUC:

df['col4'] = df.groupby('col1')['col2'].transform(lambda x: x.shift(-3)) / df['col2'] - 1

输出:

  col1  col2  col3  col4
0    A     2     4  0.50
1    A     4     5  0.75
2    A     7     7   NaN
3    A     3     8   NaN
4    A     7     3   NaN
5    B     8     9  1.50
6    B    10    10   NaN
7    B     8     9   NaN
8    B    20    15   NaN

使用transform 在每个组中移动“col2”,然后除以“col2”并减去 1。

【讨论】:

  • 非常感谢。它有效,但我仍然不明白为什么管道不起作用。
  • 您在这里使用的管道非常非传统,我不确定您是否可以像在思考一样使用它。此解决方案更适合您要完成的工作。
  • 您的 groupby 与 apply 返回正确的系列,但是您将在将其连接回原始数据框时遇到一些问题。使用变换是更好的解决方案。
  • 你能解释一下为什么 OP 对pipe 的使用是非常规的(它只是.shift(-3))吗?这本质上是一个只针对一个用例的纯代码答案,因此不是可重用的资源;请添加一些解释。
猜你喜欢
  • 2021-01-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-03-30
  • 2023-02-20
  • 1970-01-01
  • 2022-10-23
  • 1970-01-01
相关资源
最近更新 更多