使用 To_parquet 将数据帧写入二进制 Parquet 格式

Pandas 库的方法to_parquet是读取 DataFrame 并将其写入 parquet 格式。

在详细了解该to_parquet方法之前,让我们深入了解一下 Parquet 格式是什么以及为什么应该使用 Parquet。

什么是实木复合地板?

Parquet 是一种基于数据列式存储的存储格式。它主要用于大数据处理,因为它可以有效地处理和操作大型、复杂的数据。

那么你可能会问列式存储有什么用呢?那么,当数据(复杂且大型)存储在按列结构而不是行结构中时,它可以更有效地压缩和编码数据。

当以柱状结构存储时,数据变得易于查询。将数据存储在 Parquet 文件中还可以减少系统的内部输入输出操作并降低复杂性。

此外,与 CSV 不同的是,parquet 格式支持嵌套数据结构,并且与 Apache Arrow 表很好兼容。

Parquet 文件是自描述的,因此可以轻松使用 Apache Spark、Apache Impala 等处理工具进行处理。

什么是数据框?

数据框是一种二维表结构,以行和列存储值。

一个数据框可能有数千行数据,其中只有少数是有用的。查看这篇关于如何过滤数据框的文章。

下面给出了创建数据框的简单示例。

下面显示了借助字典创建数据框的代码。

1
2
3
4
5
6
7
import pandas as pd
data={
            "Height":[165,158,163],
             "Weight":[50,40,45]
}
df=pd.DataFrame(data)
print(df)

让我们快速看一下解释。

在第一行中,我们使用其标准别名 pd 将 Pandas 库导入到我们的环境中。

接下来,我们创建一个包含两个键的数据字典:Height 和 Weight。与这些键对应的值包含在方括号 [] 中。

然后在方法的帮助下将该字典转换为数据框pd.DataFrame()它存储在一个名为 df 的对象中。

在下面的行中,我们使用 打印此数据框print()

数据框

为什么要将数据框转换为 Parquet?

如您所知,数据框架是 Pandas 库中最重要且最常用的数据结构。数据框是非常强大的数据存储工具,不仅在 Python 中,而且在 R 中也是如此。

当我们谈论 Pandas 库时,必须查看这篇关于 Pandas 数据结构的文章。Pandas 模块教程

那么为什么需要将如此强大的存储工具转换为Parquet呢?

正如我们已经讨论过的,镶木地板允许足够的压缩,这对于数据帧来说可能是不可能的。
数据框可能不是存储大量数据的正确选择,因为查询可能会因为数据框而变得混乱。
此外,当数据帧转换为与 Apache 和 Julia 等其他工具兼容的 Parquet 格式时,数据交换将变得很容易,甚至可以使用这些库独有的特殊工具。
数据安全是将数据框架转换为 Parquet 的最大原因之一。
数据以镶木地板格式编码。因此,除非且直到对文件执行任何解码操作,否则数据都是安全的。

先决条件

在将数据帧写入 parquet 之前,我们必须确保系统中安装了必要的软件包。

必要的包是:

  • pyarrow
  • 快速镶木地板

pyarrow

PyArrow 也是一个 Python 库,可处理更大、更复杂的数据集。

PyArrow 提供快速、内存高效的数据结构和算法,可用于各种数据处理任务,例如从磁盘读取数据和将数据写入磁盘以及执行数据转换。

它还可用于与 Apache Spark 等发行版一起使用。

快速镶木地板

顾名思义,fastparquet 是一个专门用于处理 parquet 文件(读取和写入 parquet 格式)的库。

它的设计速度快且内存效率高,允许用户轻松处理大型数据集。

它可以与其他Python库集成,例如PyArrow和Pandas,以执行不同数据结构之间的相互转换,例如Parquet到数据框架或数据框架到Parquet。

以下是安装所需软件包的方法。

!pip install pyarrow
 
!pip install fastparquet

如何将数据帧写入_parquet?

安装软件包后,您就可以开始使用 parquet 文件格式。

to_parquet数据帧作为输入并将其写入 parquet 文件。

下面给出了的语法to_parquet

DataFrame.to_parquet(pathengine='auto'compression='snappy'index=Nonepartition_cols=None**kwargs)

重要参数是:

数字 姓名 描述 默认值 需求性
1 小路 如果对象是字符串,则在写入分区数据集时将用作根目录路径。
该路径应该是文件或类似文件的对象;这意味着它应该支持 write() 方法
引擎之一 –fastparquet 不支持类文件对象
所以fastparquet当路径是类文件时不应该使用引擎模式
str 或类文件对象 必需的
2 引擎 要使用的 parquet 库的类型
引擎可以是auto, pyarrow,fastparquet
如果pyarrow不可用,the engine is changed to fastparquet
汽车 必需的
3 压缩 要使用的压缩名称
如果不需要压缩(当文件较小时),请选择None
也可以是snappy, gzip,brotli
活泼的 必需的
4 指数 该参数决定数据帧的起始索引是否应包含在结果中 如果是
, indexTrue数据帧的索引包含在输出中
如果index为 False,则数据帧的索引为不包含在输出中
还有另一种指定索引的方法,即 RangeIndex,它有三个参数;start,stop,step
Start 表示范围应该开始的索引,Stop 给出我们需要停止考虑的值值和步长的作用类似于增量或减量运算符
现在使用它的优点RangeIndex是内存效率高;不占用太多空间

None 必需的
5 分区列 当我们希望对数据集进行分区时使用此参数它给出了数据集分区应遵循的列名称列按照
给定的顺序进行分区
如果路径不是字符串,则此参数必须为 None
列表,
默认:None
选修的
6 **夸格 其他参数将传递到 parquet 库。 必需的
论据to_parquet

在这篇文章中,我们将看到将数据帧写入 parquet、 的特殊应用partition_cols以及压缩模式(gzip、snappy 和 brotli)之间的比较。

将简单数据帧写入 Parquet 格式

让我们看一个将数据帧写入 parquet 文件的简单示例。

首先,如上所述,我们需要创建一个数据框。

代码如下:

1
2
3
4
import pandas as pd
# Create a sample DataFrame
df = pd.DataFrame({'A': [1, 2, 3,10], 'B': [4, 5, 6,11], 'C': [7, 8, 9,12], 'D':[13,14,15,16]})
print(df)

在第一行中,我们导入 Pandas 库,这对于处理数据框至关重要。

接下来,我们借助列表集合创建一个数据框,并将其存储在名为 df 的新变量中。

最后,我们使用print().

得到数据帧如下:

数据框1

现在,我们需要将此 DataFrame 写入 parquet。

此操作可以使用 来完成to_parquet

代码如下。

1
2
df.to_parquet('sample.parquet')
pd.read_parquet('sample.parquet')

在第一行中,我们使用 将数据帧转换为镶木地板to_parquetparquet 文件的名称是“sample.txt”。镶木地板’。

在下面的行中,我们使用该pd.read_parquet方法来读取 parquet 文件。

输出如下所示。

To_Parquet1

正如您可能从输出中看到的,在左端创建了一个 parquet 格式的新文件。如果您使用 anaconda 或 jupyter,该文件可能会下载到您的本地存储区域。

对 Parquet 文件进行分区

尽管partition_cols是语法中的可选字段,但它可用于有效地检索递归使用的特定数据。
该参数采用 parquet 文件和需要分区的列,并将分区的 parquet 文件存储在路径/目录中。

我们将采用之前看到的相同示例(sample.parquet)并在此文件上实现分区。

该方法的实现如下图所示:

1
df.to_parquet('/content/drive/MyDrive/parquetfile/sample.parquet',partition_cols=['A','B'],engine='fastparquet',compression='gzip')

首先,我们需要获取要使用的文件的位置。

接下来,我们将使用该位置对文件进行分区。

从上面的代码片段可以看出,我们将位置指定为路径,要分区的列是列“A”和“B”。我们使用的是fastparquet引擎,压缩模式是gzip。

我们需要创建一个目录来存储分区文件。您可以从此目录访问这些分区文件。

分区后的文件存储在路径drive->MyDrive中,目录为parquetfile。

分区文件应该如下所示。

分区文件

当您重复使用相同的数据或部分数据时,此文件分区可能会派上用场。如果 parquet 文件已分区,您可以检索要查找的内容,而不是访问整个数据文件。

gzip压缩所花费的时间

我们首先要检查 所花费的时间gzip

我们将采用相同的示例将数据帧转换为镶木地板,但使用gzip压缩。

考虑下面给出的代码:

1
2
df.to_parquet('sampl.parquet',engine='fastparquet',compression='gzip')
pd.read_parquet('sampl.parquet')

输出是 parquet 文件,如下所示。

To_Parquet2

让我们检查一下所花费的时间。

%timeit df.to_parquet('sampl.parquet',engine='fastparquet',compression='gzip')

当压缩模式为gzip时,我们检查创建“sampl.parquet”文件的时间。

%timeit模块也被称为Python的魔法模块,用于检查单行代码的执行时间。

这是上述代码的输出。

Gzip 压缩

快速压缩所需的时间

让我们检查一下使用压缩创建 parquet 文件所需的时间snappy

代码如下。

%timeit df.to_parquet('sampl.parquet',engine='fastparquet',compression='snappy')

我们正在检查创建名为“sampl.txt”的文件所需的时间。当压缩模式为 snappy 时,“parquet”。python 的模块%timeit用于此任务。

使用压缩创建 parquet 文件所需的时间snappy如下所示。

快速压缩

brotli 压缩所需的时间

最后的压缩类型是brotli.

%timeit df.to_parquet('sampl.parquet',engine='fastparquet',compression='brotli')

使用 brotli 压缩创建 parquet 文件比其他两种压缩模式需要更长的时间。

布洛特利压缩

以下是三种压缩类型的比较,供参考。

三种压缩方式对比

可以看到,压缩模式为snappy时,耗时很短,仅为3.98毫秒。由于它更快、更高效,我们大多默认使用快速压缩。

结论

总而言之,我们已经了解了 Parquet 文件格式及其用途。

我们了解了什么是数据帧以及为什么需要将数据帧转换为 Parquet 格式。

我们已经了解了如何从字典创建数据框以及将数据框写入 parquet 所需的重要包及其安装。

接下来,我们看到了该方法的语法to_parquet()及其参数的详细解释。

来看示例,首先,我们了解了如何从列表创建数据框,然后将该数据框转换为 parquet 文件。

我们还看到了转换后如何在本地存储区域中创建新的 parquet 文件。

接下来,我们看到了 的应用程序partition_cols,它用于创建分区文件段,可以帮助轻松检索常用的数据文件。

最后,我们看到了三种压缩模式(snappygzipbrotli)之间的比较,并且理解了为什么使用 snappy 作为默认压缩模式。之所以如此,是因为快速压缩从更高效的数据帧创建镶木地板文件所需的时间更少。

参考

您可以在此处找到有关此方法的更多信息

详细了解 timeit 模块以及如何测量小代码片段的执行情况

从这个堆栈溢出答案链中了解如何使用 timeit 模块