2017-08-25 85 views
1

比方说,我有两个dataframes,并同时为列名:python熊猫如何根据子串合并/连接两个表?

table 1 columns: 
[ShipNumber, TrackNumber, Comment, ShipDate, Quantity, Weight] 
table 2 columns: 
[ShipNumber, TrackNumber, AmountReceived] 

我想合并两个表时是“ShipNumber”或从表2“轨段编号”可以在“评论”中找到从表1

而且,我会解释为什么

merged = pd.merge(df1,df2,how='left',left_on='Comment',right_on='ShipNumber') 

不会在这种情况下工作。

“注释”列是可以包含任何内容的文本块,因此我无法进行类似tab2.ShipNumber == tab1.Comment的精确匹配,因为tab2.ShipNumber或tab2.TrackNumber可以作为子字符串tab1.Comment。

所需的输出表应具有的所有独特的列从两个表:

output table column names: 
[ShipNumber, TrackNumber, Comment, ShipDate, Quantity, Weight, AmountReceived] 

我希望我的问题是有道理的...... 任何帮助,真的很感谢!

的最终目标是与合并两套(shipnumber == shipnumber |轨段编号==轨段编号| shipnumber在评论|评论中轨段编号),但我已经创建了两个子集为前两个条件,现在我正在处理第三和第四个条件。

+0

你可以在''Comment''列上使用正则表达式来创建一个新的'ExtractedNum'列来匹配看起来像ShipNumber或TrackNumber的东西吗?然后你可以合并新的ExtractedNum列。或者评论中可能有多于一个的数字? – nanojohn

+0

ShipNumber和TrackNumber可能不会保持相同的格式....(少数例外存在,不想排除这些)。所以这就是为什么我想只匹配来源(表2)。和'评论'是一个文本的一块可以是任何东西。 – alwaysaskingquestions

回答

0

这是一个基于一些组成数据的例子。忽略我在数据框中输入的完整无稽之谈,我只是随便输入一些东西来获取样本df。

import pandas as pd 
import re 

x = pd.DataFrame({'Location': ['Chicago','Houston','Los Angeles','Boston','NYC','blah'], 
        'Comments': ['chicago is winter','la is summer','boston is winter','dallas is spring','NYC is spring','seattle foo'], 
        'Dir':  ['N','S','E','W','S','E']}) 

y = pd.DataFrame({'Location': ['Miami','Dallas'], 
        'Season': ['Spring','Fall']}) 


def findval(row): 
    comment, location, season = map(lambda x: str(x).lower(),row) 
    return location in comment or season in comment 

merged = pd.concat([x,y]) 

merged['Helper'] = merged[['Comments','Location','Season']].apply(findval,axis=1) 
print(merged) 
filtered = merged[merged['Helper'] == True] 
print(filtered) 

不是加入相反,你可以conatenate的dataframes,然后创建一个帮手,看看一列字符串中的另一个发现。一旦你有了这个帮手列,只需过滤掉True即可。

+0

这不起作用;抱歉没有明确提出我的问题。我现在编辑我的问题。 – alwaysaskingquestions

+0

基本上,“注释”是一个长字符串,但是shipnumber可以是包含在“注释”字符串中的子字符串。因此不能像这样使用合并功能。 – alwaysaskingquestions

+0

我不确定是否有方法可以加入函数调用 - 也许将df连接在一起,然后创建一个辅助列,其中包含're.search'或简单的'trackingnum in Comment或shipnumber in comment'。之后,您可以像正常情况下那样过滤df,以确保该帮助列是真实的。 – Solaxun

0

为什么不这样做

Count = 0 
def MergeFunction(rowElement): 
    global Count 
    df2_row = df2.iloc[[Count]] 
    if(df2_row['ShipNumber'] in rowElement['Comments'] or df2_row['TrackNumber'] 
     in rowElement['Comments'] 
    rowElement['Amount'] = df2_row['Amount'] 
    Count+=1 
    return rowElement 

df1['Amount'] = sparseArray #Fill with zeros 
new_df = df1.apply(MergeFunction) 
0

,你可以使用索引像Whoosh库中的注释字段,然后做你想要通过搜索每次发货数量文本搜索。