我有不同的数据帧,需要根据日期列将它们合并在一起。如果我只有两个数据帧,我可以使用df1.merge(df2,on='date')
,要使用三个数据帧,我可以使用df1.merge(df2.merge(df3,on='date'),on='date')
,但是使用多个数据帧会变得非常复杂和不可读。
所有数据帧都有一个公共列-date
,但它们的行数和列数都不相同,我只需要其中每个日期对每个数据帧都是公共的行。
所以,我试图编写一个递归函数,返回一个包含所有数据的数据帧,但它不起作用。那么我应该如何合并多个数据帧呢?
我尝试了不同的方法,得到了一些错误,如超出范围
,
键错误0/1/2/3
和无法将数据帧与类型的实例合并
这是我写的剧本:
dfs = [df1, df2, df3] # list of dataframes
def mergefiles(dfs, countfiles, i=0):
if i == (countfiles - 2): # it gets to the second to last and merges it with the last
return
dfm = dfs[i].merge(mergefiles(dfs[i+1], countfiles, i=i+1), on='date')
return dfm
print(mergefiles(dfs, len(dfs)))
例如:df_1:
May 19, 2017;1,200.00;0.1%
May 18, 2017;1,100.00;0.1%
May 17, 2017;1,000.00;0.1%
May 15, 2017;1,901.00;0.1%
df_2:
May 20, 2017;2,200.00;1000000;0.2%
May 18, 2017;2,100.00;1590000;0.2%
May 16, 2017;2,000.00;1230000;0.2%
May 15, 2017;2,902.00;1000000;0.2%
df_3:
May 21, 2017;3,200.00;2000000;0.3%
May 17, 2017;3,100.00;2590000;0.3%
May 16, 2017;3,000.00;2230000;0.3%
May 15, 2017;3,903.00;2000000;0.3%
预期合并结果:
May 15, 2017; 1,901.00;0.1%; 2,902.00;1000000;0.2%; 3,903.00;2000000;0.3%
functools.reduce和pd.concat是很好的解决方案,但就执行时间而言pd.concat是最好的。
from functools import reduce
import pandas as pd
dfs = [df1, df2, df3, ...]
nan_value = 0
# solution 1 (fast)
result_1 = pd.concat(dfs, join='outer', axis=1).fillna(nan_value)
# solution 2
result_2 = reduce(lambda df_left,df_right: pd.merge(df_left, df_right,
left_index=True, right_index=True,
how='outer'),
dfs).fillna(nan_value)
看起来数据具有相同的列,因此您可以:
df1 = pd.DataFrame(data1)
df2 = pd.DataFrame(data2)
merged_df = pd.concat([df1, df2])
下面是在不涉及复杂查询的情况下合并多个数据帧的最干净、最容易理解的方法。
只需简单地将DATE作为索引进行合并,然后使用OUTER方法进行合并(以获取所有数据)。
import pandas as pd
from functools import reduce
df1 = pd.read_table('file1.csv', sep=',')
df2 = pd.read_table('file2.csv', sep=',')
df3 = pd.read_table('file3.csv', sep=',')
现在,基本上将所有文件作为数据帧加载到列表中。然后,使用merge
或reduce
功能合并文件。
# compile the list of dataframes you want to merge
data_frames = [df1, df2, df3]
注意:您可以在上面的列表中添加尽可能多的数据帧。这是这个方法的优点。不涉及复杂的查询。
要保留属于同一日期的值,您需要将其合并到DATE
中。
df_merged = reduce(lambda left,right: pd.merge(left,right,on=['DATE'],
how='outer'), data_frames)
# if you want to fill the values that don't exist in the lines of merged dataframe simply fill with required strings as
df_merged = reduce(lambda left,right: pd.merge(left,right,on=['DATE'],
how='outer'), data_frames).fillna('void')
pd.DataFrame.to_csv(df_merged, 'merged.txt', sep=',', na_rep='.', index=False)
这应该给你
DATE VALUE1 VALUE2 VALUE3......
问题内容: 我有不同的数据框,需要根据日期列将它们合并在一起。如果我只有两个数据帧,则可以使用来对三个数据帧进行操作,但是,使用多个数据帧将变得非常复杂且难以读取。 所有数据框都有一个共同的列- ,但是它们没有相同数量的行或列,而我只需要每个数据框共有每个日期的那些行。 因此,我正在尝试编写一个递归函数,该函数返回一个包含所有数据的数据框,但是它不起作用。那我应该如何合并多个数据框? 我试图dif
问题内容: 所有,我必须创建一个具有基本架构的数据库。该数据库将很大(超过100GB),并将用作数据仓库。现在,该数据库的创建当前正在通过C#代码“一次命中”执行。从许多不同的来源中提取数据。由于数据量巨大,这种创建引起了一些问题。已经决定,与其一口气创建一个数据库,不如一次创建一个数据库。到 创建几个包含核心数据表的较小数据库。 将较小的数据库合并为一个较大的数据库。 建立架构/添加相关约束。
问题内容: 我整个上午都在搜索,但是大多数合并示例仅基于一个键,而在多个键上却找不到任何东西。 pid = 111,sid = 6,eid = 123的值在x和y中都匹配,然后合并为一条记录。如果它们不匹配,只需将其原样带过来。 我想要的最终结果: 问题答案: 这是从元组中重新锁定:
问题内容: 我有一个关于数据库体系结构的问题。 我们正在建立一个CMS。许多字段将具有预填充的选择。例如,客户的信用状态可以为“良好”,“不良”,“未知”或“存款”。该项目的规格是这些预先填充的选择是动态的,管理员可以通过后端添加新值。所以我需要将这些值存储在数据库中。 我正在努力在两种方法之间做出决定 1)为每种清单都有一张桌子。示例将是诸如list_CrediStatus,list_Branc
有些时候,应用程序调试日志会包含非常丰富的内容,为一个事件打印出很多行内容。这种日志通常都很难通过命令行解析的方式做分析。 而 logstash 正为此准备好了 codec/multiline 插件! 小贴士:multiline 插件也可以用于其他类似的堆栈式信息,比如 linux 的内核日志。 配置示例 input { stdin { codec => multiline
我有两个不同列数和行数的CSV文件。第一个CSV文件有M列和N行,第二个文件有H列和G行。一些列具有相同的名称。 null 另外,如果两个CSV文件有两个数据帧,并希望这样做,例如,如果我将第一个CSV加载到中,将第二个加载到中,然后希望合并到,类似于上面的示例。