根据两个 pandas DataFrames 之间的条件为新列分配值

Posted

技术标签:

【中文标题】根据两个 pandas DataFrames 之间的条件为新列分配值【英文标题】:Assign values to new column based on conditions between two pandas DataFrames 【发布时间】:2020-04-09 07:49:39 【问题描述】:

假设有两个数据框: df1 包含 4 列。 “NAME”列包含城市的名称(A、B、C)。其他每一列代表一年 (y0, y1, y2),其中包含居住在该城市的人数。

np.random.seed(seed=34)
name = ['A','B','C']
y0 = np.random.random_integers(1,high=40, size=3)
y1 = np.random.random_integers(1,high=40, size=3)
y2 = np.random.random_integers(1,high=40, size=3)
df = pd.DataFrame(data='NAME' : name, 'y0' : y0, 'y1' : y1, 'y2' : y2)
df

   NAME y0  y1  y2
0   A   34  36  15
1   B   22  6   30
2   C   5   12  19

df2 包含 3 列。 “NAME”列包含城市的名称。 “y”列包含年份的值(y0、y1、y2),“i”列包含可以访问互联网的人数。

y = ['y0', 'y1', 'y2',  'y0', 'y1', 'y2',  'y0', 'y1', 'y2']
name2 = ['A', 'A', 'A', 'B', 'B', 'B', 'C', 'C', 'C']
i = [15, 6, 12, 18, 4, 20, 3, 8, 2]
df2 = pd.DataFrame(data='NAME':name2, 'y':y, 'i':i)
df2

   NAME y   i
0   A   y0  15
1   A   y1  6
2   A   y2  23
3   B   y0  18
4   B   y1  17
5   B   y2  20
6   C   y0  3
7   C   y1  24
8   C   y2  2

我需要在 df2 上创建一个包含 df1 值的列,条件是 df2['NAME'] 的值等于 df1['NAME'] 并且 df2['y'] 等于到 df1 列,以获得以下结果:


   NAME y   i   v
0   A   y0  15  34
1   A   y1  6   36
2   A   y2  12  15
3   B   y0  18  22
4   B   y1  4   6
5   B   y2  20  30
6   C   y0  3   5
7   C   y1  8   12
8   C   y2  2   19

城市名称出现在 df 上的次数不是恒定的。 提前谢谢你。

【问题讨论】:

df2['y'] 假设等于哪一列? 它应该等于df1中的“年”(y0,y1,y2)列之一。 【参考方案1】:

您可以这样做,因为值匹配:

df2['v'] = df.melt(col_level=0, id_vars='NAME').sort_values(by='NAME').reset_index(drop=True)['value'] 

输出:

  NAME   y   i   v
0    A  y0  15  34
1    A  y1   6  36
2    A  y2  12  15
3    B  y0  18  22
4    B  y1   4   6
5    B  y2  20  30
6    C  y0   3   5
7    C  y1   8  12
8    C  y2   2  19

或使用 combinefirst

df3 = df.melt(col_level=0, id_vars='NAME').sort_values(by='NAME').reset_index(drop=True)  
df3 = df3.rename(columns='variable':'y')                                                                                         
df3 = df2.combine_first(df3)
df3['value'] = df3['value'].astype(int)


  NAME   i  value   y
0    A  15     34  y0
1    A   6     36  y1
2    A  12     15  y2
3    B  18     22  y0
4    B   4      6  y1
5    B  20     30  y2
6    C   3      5  y0
7    C   8     12  y1
8    C   2     19  y2

【讨论】:

【参考方案2】:

合并会更好,

df = pd.melt(df,id_vars='NAME',var_name='y',value_name='v')

df_new = pd.merge(df,df2,on=['NAME','y'].sort_values('NAME')
print(df_new)
  NAME   y   i   v
0    A  y0  15  34
3    A  y1   6  36
6    A  y2  12  15
1    B  y0  18  22
4    B  y1   4   6
7    B  y2  20  30
2    C  y0   3   5
5    C  y1   8  12
8    C  y2   2  19

【讨论】:

以上是关于根据两个 pandas DataFrames 之间的条件为新列分配值的主要内容,如果未能解决你的问题,请参考以下文章

根据 pandas 中的多个键合并两个 DataFrame

Pandas 通过两列左连接 DataFrames

从两个 Pandas DataFrames 向数据帧添加一列,当前使用两个带有条件的循环:有更快的方法吗?

使用 tensorflow 的 LinearClassifier 和 Panda 的 Dataframes 构建 SVM

合并pandas DataFrames时如何保留列MultiIndex值

pandas 有效地将 DataFrames 与不匹配的分类列和 MultiIndex 级别连接起来