2017-05-27 3 views
0

を返します。は、私は2つのデータフレームを持つデータフレーム間の値を比較し、対応する値に

for index1, row1 in df1.iterrows(): 
    for index2, row2 in df2.iterrows(): 
     if (row1['df1_A'] >= row2['df2_A']) & (row1['df1_A'] <= row2['df2_B']): 
      row1['df1_C'] = row2['df2_C'] 

これを書くための最も簡単で読みやすい方法は、それが周りに240万回ループしているので、私のプログラムのパフォーマンスが低下し、ループのための2つを使用することであるが、。私の仕事を達成する良い方法がありますか?

+0

は私達にあなたのループのコードを表示します。私はdf2_Cの値がdf1_C **に返されるべきかどうかを知ることができません。 –

+0

コードを追加しました。これは私が私と一緒に持っていたロジックですが、反復しなければならないループの数のために困惑しています。 –

答えて

0

OK、あなたのループのコードがあるように、言い換え:

for row1 in df1.rows: 
    for row2 in df2.rows: 
     if (row1.A >= row2.A) & (row1.A <= row2.B): 
      row1.C = row2.C 

はのは、ループを反転してみましょう:それは3回だけ実行されるため、今

for row2 in df2.rows: 
    for row1 in df1.rows: 
     if (row1.A >= row2.A) & (row1.A <= row2.B): 
      row1.C = row2.C 

、外側のループを除去することは非常に重要ではありません。のは、内側の部分をベクトル化してみましょう:

for row2 in df2.rows: 
    df1.C[(df1.A >= row2.A) & (df1.A <= row2.B)] = row2.C 

そして簡素化:

for row2 in df2.rows: 
    df1.C[df1.A.between(row2.A, row2.B)] = row2.C 

私はそれが十分に良いです願っています。これがどんなに速いかをお知らせください。

0

には3行しか含まれていないという事実を使用しましょう!

セットアップ:

df1 = pd.DataFrame(np.random.randint(100, size=(10**6, 1)), columns=['val']) 

df2 = pd.DataFrame({'A': {0: 1, 1: 10, 2: 20}, 'B': {0: 5, 1: 13, 2: 20}}) 

ソリューション:

qry = ' | '.join(['{0[0]}<=val<={0[1]}'.format(r) for r in df2.values.tolist()]) 

df1.query(qry) 

タイミング: 1.000.000行のDF:

は、次のベクトル化のアプローチを考えてみましょう

In [34]: df1.shape 
Out[34]: (1000000, 1) 

In [35]: %timeit df1.query(qry) 
10 loops, best of 3: 46.6 ms per loop 

生成されたクエリ:

In [36]: qry 
Out[36]: '1<=val<=5 | 10<=val<=13 | 20<=val<=20' 
関連する問題