Parquetとは?読み方・仕組み・CSVとの違いをわかりやすく解説
Parquet(パーケ)は、大量のデータを高速かつ低コストに分析するために設計された「列指向」のファイル形式です。AWS AthenaやGoogle BigQuery、Apache Sparkといった分析基盤で広く使われており、CSVを置き換える標準的なデータ形式として定着しています。本記事では、Parquetの読み方や仕組み、CSV・JSON・Avroとの違い、Python(pandas / PyArrow)での使い方までを、実例を交えて解説します。
目次
まとめ:Parquetの要点
先に結論をまとめます。詳細は本文で順番に解説します。
- Parquetとは:列単位でデータを保存する「列指向(カラムナ)」のオープンソースなファイル形式。分析(OLAP)用途に最適化されています。
- 読み方:「パーケ」「パーケット」「パルケ」などと読まれます。決まった公式の読みはなく、日本では「パーケット」が比較的よく使われます。
- 速い理由:必要な列だけを読み込み(列プルーニング)、ファイルに持つ統計メタデータで不要なデータの読み飛ばしができるため、CSVより圧倒的に高速です。
- 軽い理由:同じ型のデータが連続するため圧縮が効きやすく、CSVより大幅に小さくなります(後述の実測ではCSVの約1/8)。
- 使いどころ:データレイク/データウェアハウスでの大規模分析。単体は「テーブル」ではないため、テーブル機能はApache IcebergやDelta Lakeが補います。
それでは、まず読み方と基本概念から見ていきましょう。
Parquetとは(読み方・基本概念)
Parquetは、Apache Software Foundationが管理するオープンソースの列指向データファイル形式です。データを列単位で格納するため、特定の列だけを対象とする集計・分析を高速に実行できます。2013年にTwitterとClouderaによって開発され、その後2015年にApacheのトップレベルプロジェクトに昇格しました。現在はAWS・Google Cloud・Azureの主要クラウドでサポートされ、ビッグデータ分析の事実上の標準フォーマットになっています。
読み方は「パーケ」「パーケット」「パルケ」など複数あり、公式に定められた唯一の読みはありません。元はフランス語で寄木張りの床を指す言葉で、列(板)を並べて構造を作るイメージと重なります。ファイルの拡張子は .parquet です。
Parquetの仕組み:列指向(カラムナ)ストレージとは
Parquetの特徴を理解する鍵は「行指向」と「列指向」の違いにあります。同じ表データでも、ディスク上での並べ方が根本的に異なります。
行指向(CSV)と列指向(Parquet)の違い
CSVのような行指向形式は、1行分のデータをまとめて順番に保存します。1件ずつ追加・更新する処理には向きますが、「price列だけを集計したい」場合でも全列を読み込む必要があります。一方Parquetは列単位で保存するため、必要な列だけをピンポイントで読み込めます。次のような表データを例にすると、CSVは「1,apple,100 / 2,banana,120…」と行ごとに、Parquetは「id列:1,2,3 / name列:apple,banana,orange / price列:100,120,150」と列ごとにまとめて格納するイメージです。
なぜParquetは分析が速いのか
Parquetが分析で速い理由は、主に次の3点です。第一に列プルーニングで、クエリに必要な列だけを読み込み、I/Oを削減します。第二に統計メタデータで、後述の行グループ単位で各列の最小値・最大値・NULL数などを保持しており、条件に合致しないデータ範囲をまるごと読み飛ばせます(述語プッシュダウン)。第三にスキーマとバイナリ形式で、データ型が明確に保持されているため、テキストのパースが不要で処理効率が高くなります。
Parquetのファイル構造(行グループ・カラムチャンク・メタデータ)
Parquetファイルは階層構造を持ちます。ファイルは複数の行グループ(Row Group)に分割され、各行グループは列ごとのカラムチャンク(Column Chunk)を持ち、さらにページ(Page)という最小単位に分かれます。ファイルの先頭と末尾には識別子「PAR1」が置かれ、末尾のフッターにスキーマや各列の圧縮・エンコーディング情報、そして統計値(min/max/null_count)といったメタデータがまとめられています。
このメタデータがあることで、クエリエンジンはファイル全体を読まずに「どの行グループを読むべきか」を判断できます。Parquet自体に一般的なデータベースのようなインデックスはありませんが、この統計情報が実質的にインデックスに近い役割を果たし、スキャン量を削減します。
Parquetの圧縮(Snappy・Gzip・Zstd)
Parquetは2段階でデータを小さくします。まず列内のデータ特性を活かしたエンコーディング(辞書エンコーディング、ランレングスエンコーディングなど)でデータ量を削減し、その上で圧縮コーデックを適用します。代表的なコーデックは用途に応じて選びます。
- Snappy:圧縮・解凍が高速。読み書きの速度を重視する分析用途の既定値としてよく使われます。Sparkなどの出力ファイル名が
part-00000.snappy.parquetのようになるのはこのためです。 - Gzip:圧縮率が高くストレージ削減に有利。一方でCPU負荷は高めです。
- Zstd:速度と圧縮率のバランスが良く、近年採用が増えています。
圧縮方式はファイルのメタデータに記録されるため、読み込み側が方式を意識せずに展開できます。圧縮はファイル全体ではなく列(カラムチャンク)単位で行われる点もポイントです。
ParquetとCSV・JSON・Avroの違い(比較表)
データ形式は用途で使い分けます。Parquetは分析(OLAP)に、CSV/JSONは可読性や交換用途に、Avroは行単位の書き込みやスキーマ進化に強みがあります。主な違いを整理します。
| 項目 | CSV | JSON | Avro | Parquet |
|---|---|---|---|---|
| 格納方式 | 行指向 | 行指向 | 行指向 | 列指向 |
| 形式 | テキスト | テキスト | バイナリ | バイナリ |
| スキーマ保持 | なし | なし | あり | あり |
| 圧縮効率 | 低 | 低 | 中 | 高 |
| 分析クエリ | 遅い | 遅い | 中 | 速い |
| 得意用途 | 交換 | API | 書込 | 分析 |
大規模データの集計や分析を高速・低コストで行いたい場合は、Parquetが最適な選択肢になります。逆に、人が直接編集する小さなデータや他システムとの単純な受け渡しにはCSVが適しています。
Pythonでの使い方(pandas / PyArrow)
PythonではpandasとPyArrowでParquetを簡単に扱えます。まず必要なライブラリを導入します。
pip install pandas pyarrow
pandasの to_parquet / read_parquet で読み書きできます。columns を指定すれば、必要な列だけを読み込む列プルーニングが効きます。
import pandas as pd
df = pd.DataFrame({
"id": [1, 2, 3, 4],
"category": ["A", "A", "B", "B"],
"price": [100, 120, 150, 180],
})
# 書き込み(Snappy圧縮)
df.to_parquet("sample.parquet", engine="pyarrow", compression="snappy")
# 必要な列だけ読む
only_price = pd.read_parquet("sample.parquet", columns=["price"])
print(only_price)
PyArrowを使うと、スキーマや行数などのメタデータを直接確認できます。
import pyarrow.parquet as pq
pf = pq.ParquetFile("sample.parquet")
print("rows:", pf.metadata.num_rows) # rows: 4
print("row_groups:", pf.metadata.num_row_groups) # row_groups: 1
print(pf.schema) # id / category / price の型を表示
圧縮の効果は実データで確認すると分かりやすくなります。20万行のサンプルを生成し、CSVとParquet(Snappy)で書き出してファイルサイズを比べてみます。
import pandas as pd, numpy as np, os
rng = np.random.default_rng(42)
n = 200_000
df = pd.DataFrame({
"date": rng.choice(pd.date_range("2025-01-01", periods=90).astype(str), n),
"category": rng.choice(["A", "B", "C", "D", "E"], n),
"region": rng.choice(["east", "west", "north", "south"], n),
"price": rng.integers(100, 1000, n),
})
df.to_csv("demo.csv", index=False)
df.to_parquet("demo.parquet", engine="pyarrow", compression="snappy")
print(os.path.getsize("demo.csv")) # 例: 4,500,123 bytes
print(os.path.getsize("demo.parquet")) # 例: 561,139 bytes(約1/8)
圧縮率はデータの中身やライブラリのバージョンによって変わりますが、同じ型の値が列ごとに並ぶParquetでは圧縮が強く効き、テキスト形式のCSVより大幅に小さくなることが分かります。
なお、Parquetファイルはpandasだけでなく、SQLで直接クエリすることもできます。DuckDBやAWS Athena、Google BigQuery、Apache Sparkはいずれもストレージ上のParquetをそのまま読み取れるため、ETLを最小限にしたサーバーレスな分析が可能です。
Parquetのユースケースと位置づけ(データレイクとIceberg/Delta Lake)
Parquetは、データレイク/データレイクハウスでの大規模分析、機械学習のトレーニングデータ、ログやストリーミングデータの蓄積など、幅広い場面で使われます。クラウドストレージ(S3やGoogle Cloud Storage)に保存したParquetを、クエリエンジンが直接読み取る構成が一般的です。
ただしParquetはあくまで「ファイル形式」であり、それ単体では更新・トランザクション・スキーマ変更履歴といった「テーブル」としての機能を持ちません。これらを担うのがテーブルフォーマットで、Apache IcebergやDelta Lakeは、多数のParquetファイルを1つのテーブルとして扱い、ACIDトランザクションやタイムトラベル(履歴参照)を実現します。また、DuckDBのような軽量分析エンジンを使えば、ローカルでParquetを高速にSQL分析できます。
Parquetを使うときの注意点
強力なParquetですが、運用で気をつけたい点もあります。第一に小さなファイルの大量発生です。ストリーミングなどで小さなParquetを大量に作ると、ファイルを開く際のメタデータ読み取りが積み重なり、かえって遅くなります。一定サイズ(おおむね数百MB前後)にまとめる、Sparkならcoalesceやrepartitionで結合するなどの対策が有効です。
第二にスキーマ変更(スキーマ進化)です。Parquetはスキーマを持つため、列の型変更や追加・削除を重ねると、過去ファイルとの互換性に注意が必要になります。テーブルとして履歴やスキーマ変更を安全に扱いたい場合は、前述のApache IcebergやDelta Lakeを併用するのが定石です。第三に、Parquetはバイナリ形式のためテキストエディタで直接開けません。中身の確認にはpandasやPyArrow、専用ビューアを使います。
よくある質問(FAQ)
Q. Parquetの読み方は?
A. 「パーケ」「パーケット」「パルケ」などと読まれます。公式に唯一の読みが定められているわけではありません。
Q. ParquetとCSVの違いは?
A. CSVは行指向のテキスト形式でスキーマを持ちません。Parquetは列指向のバイナリ形式でスキーマを持ち、必要な列だけ読めるため分析が高速で、ファイルも小さくなります。
Q. ParquetとIcebergの違いは?
A. Parquetは「ファイル形式」、Apache Icebergは複数のParquetファイルをまとめて管理する「テーブル形式」です。両者は競合ではなく、Icebergの下層にParquetが使われる関係です。
Q. 圧縮はどれを選べばよい?
A. 読み書き速度重視ならSnappy、ストレージ削減重視ならGzip、バランス重視ならZstdが目安です。分析基盤ではSnappyが既定としてよく使われます。
Q. ファイルの拡張子は?
A. .parquet です。Snappy圧縮の場合は xxxx.snappy.parquet のように圧縮方式を含む名前になることもあります。