jon*_*nas 319 python csv concatenation dataframe pandas
我想从目录中读取几个csv文件到pandas并将它们连接成一个大的DataFrame.我虽然无法弄明白.这是我到目前为止:
import glob
import pandas as pd
# get data file names
path =r'C:\DRO\DCL_rawdata_files'
filenames = glob.glob(path + "/*.csv")
dfs = []
for filename in filenames:
dfs.append(pd.read_csv(filename))
# Concatenate all data into one DataFrame
big_frame = pd.concat(dfs, ignore_index=True)
Run Code Online (Sandbox Code Playgroud)
我想在for循环中需要一些帮助???
Gau*_*ngh 372
如果您的所有csv文件中都有相同的列,则可以尝试以下代码.我已添加,header=0以便在读取csv第一行后可以指定为列名.
import pandas as pd
import glob
path = r'C:\DRO\DCL_rawdata_files' # use your path
all_files = glob.glob(path + "/*.csv")
li = []
for filename in all_files:
df = pd.read_csv(filename, index_col=None, header=0)
li.append(df)
frame = pd.concat(li, axis=0, ignore_index=True)
Run Code Online (Sandbox Code Playgroud)
Sid*_*Sid 257
path = r'C:\DRO\DCL_rawdata_files' # use your path
all_files = glob.glob(os.path.join(path, "*.csv")) # advisable to use os.path.join as this makes concatenation OS independent
df_from_each_file = (pd.read_csv(f) for f in all_files)
concatenated_df = pd.concat(df_from_each_file, ignore_index=True)
# doesn't create a list, nor does it append to one
Run Code Online (Sandbox Code Playgroud)
Jos*_*n H 45
import glob, os
df = pd.concat(map(pd.read_csv, glob.glob(os.path.join('', "my_files*.csv"))))
Run Code Online (Sandbox Code Playgroud)
MrF*_*Fun 39
导入两个或多个csv's 而不必列出名称。
import glob
import pandas as pd
df = pd.concat(map(pd.read_csv, glob.glob('data/*.csv')))
Run Code Online (Sandbox Code Playgroud)
Jou*_*nen 25
Dask库可以从多个文件中读取数据帧:
>>> import dask.dataframe as dd
>>> df = dd.read_csv('data*.csv')
Run Code Online (Sandbox Code Playgroud)
(来源:http://dask.pydata.org/en/latest/examples/dataframe-csv.html)
Dask数据帧实现了Pandas数据帧API的子集.如果所有数据都适合内存,则可以调用df.compute()将数据帧转换为Pandas数据帧.
rob*_*smt 22
这里几乎所有的答案都是不必要的复杂(全局模式匹配)或依赖其他第三方库.您可以使用Pandas和python(所有版本)已经内置的所有内容在2行中执行此操作.
对于一些文件 - 1个班轮:
df = pd.concat(map(pd.read_csv, ['data/d1.csv', 'data/d2.csv','data/d3.csv']))
Run Code Online (Sandbox Code Playgroud)
对于许多文件:
from os import listdir
filepaths = [f for f in listdir("./data") if f.endswith('.csv')]
df = pd.concat(map(pd.read_csv, filepaths))
Run Code Online (Sandbox Code Playgroud)
这个设置df的pandas线使用了3个东西:
pd.read_csv()iterable(我们的列表),它是filepaths中的每个csv元素).SKG*_*SKG 12
编辑:我用谷歌搜索到/sf/answers/1486299461/.然而,最近我发现使用numpy进行任何操作然后将其分配给数据帧而不是在迭代的基础上操纵数据帧本身更快,它似乎也适用于此解决方案.
我真诚地希望任何人都能在这个页面上考虑这种方法,但是不要将这段巨大的代码作为评论附加在一起并使其不那么易读.
您可以利用numpy来加速数据帧连接.
import os
import glob
import pandas as pd
import numpy as np
path = "my_dir_full_path"
allFiles = glob.glob(os.path.join(path,"*.csv"))
np_array_list = []
for file_ in allFiles:
df = pd.read_csv(file_,index_col=None, header=0)
np_array_list.append(df.as_matrix())
comb_np_array = np.vstack(np_array_list)
big_frame = pd.DataFrame(comb_np_array)
big_frame.columns = ["col1","col2"....]
Run Code Online (Sandbox Code Playgroud)
时间统计:
total files :192
avg lines per file :8492
--approach 1 without numpy -- 8.248656988143921 seconds ---
total records old :1630571
--approach 2 with numpy -- 2.289292573928833 seconds ---
Run Code Online (Sandbox Code Playgroud)
muo*_*uon 12
一个班轮使用map,但如果你想指定额外的参数,你可以这样做:
import pandas as pd
import glob
import functools
df = pd.concat(map(functools.partial(pd.read_csv, sep='|', compression=None),
glob.glob("data/*.csv")))
Run Code Online (Sandbox Code Playgroud)
注意:map它本身不允许您提供额外的参数。
tot*_*ico 10
如果要以递归方式搜索(Python 3.5或更高版本),可以执行以下操作:
from glob import iglob
import pandas as pd
path = r'C:\user\your\path\**\*.csv'
all_rec = iglob(path, recursive=True)
dataframes = (pd.read_csv(f) for f in all_rec)
big_dataframe = pd.concat(dataframes, ignore_index=True)
Run Code Online (Sandbox Code Playgroud)
请注意,最后三行可以用一行表示:
df = pd.concat((pd.read_csv(f) for f in iglob(path, recursive=True)), ignore_index=True)
Run Code Online (Sandbox Code Playgroud)
你可以在** 这里找到文档.此外,我使用iglob而不是glob,因为它返回迭代器而不是列表.
编辑:多平台递归函数:
您可以将上述内容包装到多平台功能(Linux,Windows,Mac)中,这样您就可以:
df = read_df_rec('C:\user\your\path', *.csv)
Run Code Online (Sandbox Code Playgroud)
这是功能:
from glob import iglob
from os.path import join
import pandas as pd
def read_df_rec(path, fn_regex=r'*.csv'):
return pd.concat((pd.read_csv(f) for f in iglob(
join(path, '**', fn_regex), recursive=True)), ignore_index=True)
Run Code Online (Sandbox Code Playgroud)
import glob
import pandas as pd
list_of_csv_files = glob.glob(directory_path + '/*.csv')
list_of_csv_files.sort()
df = pd.concat(map(pd.read_csv, list_of_csv_files), ignore_index=True)
Run Code Online (Sandbox Code Playgroud)
笔记:
默认情况下,生成的文件列表glob.glob是不排序的。另一方面,在许多场景中,需要对其进行排序,例如,人们可能想要分析传感器帧丢失的数量与时间戳。
在pd.concat命令中,如果ignore_index=True未指定,则它保留每个数据帧(即列表中的每个单独的 CSV 文件)的原始索引,并且主数据帧看起来像
timestamp id valid_frame
0
1
2
.
.
.
0
1
2
.
.
.
Run Code Online (Sandbox Code Playgroud)
使用ignore_index=True,它看起来像:
timestamp id valid_frame
0
1
2
.
.
.
108
109
.
.
.
Run Code Online (Sandbox Code Playgroud)
IMO,当人们可能想要手动创建帧丢失数量与一分钟(或任何其他持续时间)箱的直方图并且想要基于第一个时间戳进行计算时,这很有帮助,例如
begin_timestamp = df['timestamp'][0]
如果没有,ignore_index=True,df['timestamp'][0]会生成包含所有单独数据帧的第一个时间戳的系列,它不仅仅给出一个值。
如果多个 csv 文件被压缩,您可以使用 zipfile 读取全部并连接如下:
import zipfile
import pandas as pd
ziptrain = zipfile.ZipFile('yourpath/yourfile.zip')
train = []
train = [ pd.read_csv(ziptrain.open(f)) for f in ziptrain.namelist() ]
df = pd.concat(train)
Run Code Online (Sandbox Code Playgroud)
另一个具有列表理解的在线,它允许使用 read_csv 的参数。
df = pd.concat([pd.read_csv(f'dir/{f}') for f in os.listdir('dir') if f.endswith('.csv')])
Run Code Online (Sandbox Code Playgroud)
使用pathlib库的替代方法(通常优先于os.path)。
这种方法避免了对 pandas concat()/ 的迭代使用apped()。
来自 pandas 文档:
值得注意的是 concat()(以及因此 append())制作了数据的完整副本,并且不断重用此函数会造成显着的性能损失。如果您需要对多个数据集使用该操作,请使用列表推导式。
import pandas as pd
from pathlib import Path
dir = Path("../relevant_directory")
df = (pd.read_csv(f) for f in dir.glob("*.csv"))
df = pd.concat(df)
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
304469 次 |
| 最近记录: |