我有这本字典:
j = {1: {'help': 2},
2: {'chocolate': 1, 'help': 1},
3: {'chocolate': 1, 'help': 1}}
和此数据框:
df = pd.DataFrame({'docId': [1, 2, 3, 1, 2, 3, ],
'sent': ['help', 'chocolate', 'chocolate', 'help', 'help', 'help']})
并且我想根据docId和term匹配值,因此它应该像这样:
docId sent freq
1 help 2
2 chocolate 1
3 chocolate 1
1 help 2
2 help 1
3 help 1
我不确定如何完成此操作,我正在尝试使用地图和应用程序,但是却一无所获。
答案 0 :(得分:6)
使用元组作为键,您可以在压缩列上map
get
方法
J = {(x, y): v for x, V in j.items() for y, v in V.items()}
df.assign(freq=[*map(J.get, zip(df.docId, df.sent))])
docId sent freq
0 1 help 2
1 2 chocolate 1
2 3 chocolate 1
3 1 help 2
4 2 help 1
5 3 help 1
您可以在lambda
中使用map
,它接受两个参数并传递提供参数的可迭代对象。
df.assign(freq=[*map(lambda x, y: j[x][y], df.docId, df.sent)])
docId sent freq
0 1 help 2
1 2 chocolate 1
2 3 chocolate 1
3 1 help 2
4 2 help 1
5 3 help 1
答案 1 :(得分:5)
列表理解如何?您可以链接两个dict.get
调用(每个嵌套级别一个)。
df['freq'] = [
j.get(x, {}).get(y, np.nan) for x, y in df[['docId', 'sent']].values]
df
docId sent freq
0 1 help 2
1 2 chocolate 1
2 3 chocolate 1
3 1 help 2
4 2 help 1
5 3 help 1
如果可以保证所有条目都存在于j
中,则可以将以上内容简化为
df['freq'] = [j[x][y] for x, y in df[['docId', 'sent']].values]
df
docId sent freq
0 1 help 2
1 2 chocolate 1
2 3 chocolate 1
3 1 help 2
4 2 help 1
5 3 help 1
答案 2 :(得分:4)
IIUC使用reindex
s=pd.DataFrame(j).stack().reindex(pd.MultiIndex.from_arrays([df.sent,df.docId])).reset_index()
s
Out[81]:
sent docId 0
0 help 1 2.0
1 chocolate 2 1.0
2 chocolate 3 1.0
3 help 1 2.0
4 help 2 1.0
5 help 3 1.0
使用此方法lookup
df['Freq']=pd.DataFrame(j).lookup(df.sent,df.docId)
df
Out[95]:
docId sent Freq
0 1 help 2.0
1 2 chocolate 1.0
2 3 chocolate 1.0
3 1 help 2.0
4 2 help 1.0
5 3 help 1.0