2016-09-20 52 views
1

我一直在嘗試這一段時間,並且卡住了。這裏是問題:使用其他數據框替換數據幀中的值並將字符串作爲鍵與熊貓

我正在處理一些關於我在CSV文件中的文本的元數據。它看起來像這樣:

enter image description here

真正的表是更長,更復雜,但是也遵循同樣的邏輯:每一行是一個文本,每列是文本的不同方面。我在一些專欄中有很多變化,我希望它能夠更簡單地進行改造。例如,從敘述角度改變同源性和自動性的價值觀到非異源性的價值觀。我定義在另一個CSV文件中這種新的模式稱爲關鍵字,看起來像這樣:

enter image description here

正如你所看到的,元數據的每一列成爲行新模式的關鍵字,在舊值在term_value列中,新值在new_model列中。

所以我需要映射或使用熊貓來替換這個值。這是我得到了現在:

import re 
import pandas as pd 

df_metadata = pd.read_csv("/metadata.csv", encoding="utf-8", sep=",") 
df_keywords = pd.read_csv("/keywords.csv", encoding="utf-8", sep="\t") 

for column_metadata,value_metadata in df_metadata.iteritems(): 

    if str(column_metadata) in list(df_keywords.loc[:,"term_type"]): 

     df_metadata.loc[df_metadata[column_metadata] == value_metadata, column_metadata] = df_keywords.loc[df_keywords["term_value"] == value_metadata, ["new_model"]] 

和Python總是給這個錯誤回:

"ValueError: Series lengths must match to compare"

我認爲這個問題是在的第二部分的value_metadata與LOC替換,我這裏的意思:

df_keywords.loc[df_keywords["term_value"] == value_metadata, ["new_model"]] 

我不明白的是爲什麼value_metadata作品在此命令的第一部分,但在第二個沒有做......

請,我將不勝感激任何幫助。也許有比遍歷數據框更簡單的方法...我對任何建議都非常開放。最好的問候, 何塞

回答

1

你可以先通過slicers和由舊環map新的價值創造df_keywordsMultiindex更快的選擇:

df_keywords.set_index(['term_type','term_value'], inplace=True) 

idx = pd.IndexSlice 
#first maping in column narrative-perspective 
print (df_keywords.loc[idx['narrative-perspective',:]].to_dict()['new_model']) 
{'heterodiegetic': 'heterodiegetic', 'other/mixed': 'n-heterodiegetic', 
'homodiegetic': 'n-heterodiegetic', 'autodiegetic': 'n-heterodiegetic'} 

#column names for replacing  
L = ['narrative-perspective','narrator','protagonist-gender'] 
for col in L: 
    df_metadata[col] = 
    df_metadata[col].map(df_keywords.loc[idx[col,:]].to_dict()['new_model']) 

print (df_metadata) 
    idno author-name narrative-perspective  narrator protagonist-gender 
0 ne0001  Baroja  n-heterodiegetic third-person    male 
1 ne0002  Galdos  heterodiegetic third-person    n-male 
2 ne0003  Galdos  n-heterodiegetic third-person    male 
3 ne0004  Galdos  n-heterodiegetic third-person    n-male 
4 ne0005  Galdos  heterodiegetic third-person    n-male 
5 ne0006  Galdos  heterodiegetic third-person    male 
6 ne0007  Sawa  heterodiegetic third-person    n-male 
7 ne0008 Zamacois  heterodiegetic third-person    n-male 
8 ne0009  Galdos  heterodiegetic third-person    n-male 
9 ne0011  Galdos  n-heterodiegetic n-third-person    male 

to_dict可以被遺漏的,然後通過Series地圖:

df_keywords.set_index(['term_type','term_value'], inplace=True) 
idx = pd.IndexSlice 

#first maping in column narrative-perspective 
print (df_keywords.loc[idx['narrative-perspective',:]]['new_model']) 
term_value 
autodiegetic  n-heterodiegetic 
heterodiegetic  heterodiegetic 
homodiegetic  n-heterodiegetic 
other/mixed  n-heterodiegetic 
Name: new_model, dtype: object 

L = ['narrative-perspective','narrator','protagonist-gender'] 
for col in L: 
    df_metadata[col] = df_metadata[col].map(df_keywords.loc[idx[col,:]]['new_model']) 

print (df_metadata) 
    idno author-name narrative-perspective  narrator protagonist-gender 
0 ne0001  Baroja  n-heterodiegetic third-person    male 
1 ne0002  Galdos  heterodiegetic third-person    n-male 
2 ne0003  Galdos  n-heterodiegetic third-person    male 
3 ne0004  Galdos  n-heterodiegetic third-person    n-male 
4 ne0005  Galdos  heterodiegetic third-person    n-male 
5 ne0006  Galdos  heterodiegetic third-person    male 
6 ne0007  Sawa  heterodiegetic third-person    n-male 
7 ne0008 Zamacois  heterodiegetic third-person    n-male 
8 ne0009  Galdos  heterodiegetic third-person    n-male 
9 ne0011  Galdos  n-heterodiegetic n-third-person    male 
+0

哇,很多很多謝謝! :) 有用!你會提出什麼建議作爲最好的方法來創建元數據的列表,以重塑取決於兩個文件的輸入?因爲現在我有這三列,但明天我可能有20 ...我做到了這一點,它的工作原理,但肯定你有更好的方式: ' list_ = []; (df_keywords.loc [:,「term_type」])中的str(column_name): list_.append(column_name); print(list_); ' 我不會讓評論的代碼渲染好:(對不起! –

+0

我認爲最簡單的是['drop_duplicates'](http://pandas.pydata.org/pandas-docs/stable/)生成/ pandas.Series.drop_duplicates.html) - 'print(df_keywords.term_type.drop_duplicates()。tolist())' – jezrael

+0

很多很多謝謝!祝你有美好的一天! –