2016-11-29 13 views
0

問題があり、解決策を見つけましたが、間違っていると感じています。たぶん、より正式な方法があります。パンダ(Python) - 条件と異なる列を持つ別のものからデータフレームの列を更新する

私はすでにhad an answer for a really similar problemですが、ここでは各データフレームに同じ量の行がありません。申し訳ありませんが "ダブル投稿"が、最初のものはまだ有効ですので、新しいものを作る方が良いと思います。

問題

私は余分な列を持たずに、既存に関する情報を消去せずにマージしたい2つのデータフレームを持っています。例:

既存のデータフレーム(DF)

A A2 B 
0 1 4 0 
1 2 5 1 
2 2 5 1 

DATAFRAMEは

A A2 B 
0 1 4 2 
1 3 5 2 

は私がdf2dfを更新したいと思います(DF2)マージする場合は、列 'A' と 'A2' に相当します。 結果は次のようになります。ここでは

A A2 B 
0 1 4 2 <= Update value ONLY 
1 2 5 1 
2 2 5 1 

は私の解決策ですが、私はそれが本当に良いものではないと思います。

import pandas as pd 

df = pd.DataFrame([[1,4,0],[2,5,1],[2,5,1]],columns=['A','A2','B']) 

df2 = pd.DataFrame([[1,4,2],[3,5,2]],columns=['A','A2','B']) 

df = df.merge(df2,on=['A', 'A2'],how='left') 
df['B_y'].fillna(0, inplace=True) 
df['B'] = df['B_x']+df['B_y'] 
df = df.drop(['B_x','B_y'], axis=1) 
print(df) 

私は、このソリューションを試してみました:

rows = (df[['A','A2']] == df2[['A','A2']]).all(axis=1) 
df.loc[rows,'B'] = df2.loc[rows,'B'] 

しかし、私は理由行の間違った数のこのエラーを持っている:

ValueError: Can only compare identically-labeled DataFrame objects 

は、誰もが行うには良い方法を持っていますか? ありがとう!

答えて

1

DataFramesの両方で同じ行であることを確認するためにDataFrame.isinを使用できると思います。次にNaNmaskで作成し、combine_firstで埋めます。 intへの最終キャスト:ブールマスクが作成されます、あなたはそれが仕事を得ることができる方法でマイナーな微調整して

mask = df[['A', 'A2']].isin(df2[['A', 'A2']]).all(1) 
print (mask) 
0  True 
1 False 
2 False 
dtype: bool 

df.B = df.B.mask(mask).combine_first(df2.B).astype(int) 
print (df) 
    A A2 B 
0 1 4 2 
1 2 5 1 
2 2 5 1 
+0

ありがとうございます!それほど簡単ではありませんが、私はこれを分析/学習/使用します:D – Lerenn

1

cols = ['A', 'A2'] 
# Slice it to match the shape of the other dataframe to compare elementwise 
rows = (df[cols].values[:df2.shape[0]] == df2[cols].values).all(1) 
df.loc[rows,'B'] = df2.loc[rows,'B'] 
df 

enter image description here

関連する問題