おもこん

おもこんは「思いつくままにコンピュターの話し」の省略形です

Python初級者のお勉強ノート(19)csvモジュール

PythonCSVファイルを扱う方法:csvモジュールの基本と応用

CSVファイルは、表形式のデータをテキスト形式で保存するための一般的なフォーマットです。 この記事では、Pythoncsvモジュールを使用してCSVファイルを扱う方法について説明します。 CSVデータを効率よく操作するためのプログラム例も紹介します。

CSVとは何か?

CSV(Comma-Separated Values)は、表形式のデータをカンマ(,)区切りで記述したテキスト形式のデータフォーマットです。 行ごとにデータを区切り、各行は複数の値を含みます。たとえば以下のような形式が一般的です。

都道府県,人口,面積,企業数,学校数
東京都,13929286,2194,104934,1224
大阪府,8839469,1904,71283,903

CSVの特徴: - テキスト形式で軽量。 - 表計算ソフトやデータベースと容易にやり取り可能。 - 読み書きが簡単だが、構造が複雑なデータには向かない。

表形式のデータのPythonでの実装方法

Pythonで表形式のデータを扱うには主に以下の2つの方法があります。 その具体例は、後述のプログラム例を参考にしてください。

  1. 二重リスト(リストのリスト)

    • 各行をリストとして、全体をリストに格納。先頭行がタイトルの場合が多いが、タイトルなしで本体のみのCSVでも可能。
    • メリット: シンプルで、データの順序がそのまま反映される。
    • デメリット: 各値にアクセスする際、インデックスを使用するため、列名がないと可読性が低下。
  2. 辞書(リストの辞書)

    • 各行を辞書で表現し、全体をリストに格納。CSVの先頭行がタイトル行であることが必要。
    • メリット: 各値に列名でアクセス可能。
    • デメリット: 辞書化する手間がかかる。

Pythoncsvモジュールの使い方

csvモジュールは、PythonCSVファイルを扱うための標準モジュールです。 以下のプログラム例では、都道府県ごとのデータをCSVファイルに保存し、それを二重リスト形式および辞書形式で読み込みます。

プログラム例1: 二重リスト形式での保存と読み込み

import csv

# データ
data = [
    ["都道府県", "人口", "面積", "企業数", "学校数"],
    ["東京都", 13929286, 2194, 104934, 1224],
    ["大阪府", 8839469, 1904, 71283, 903],
]

# CSVファイルへの保存
with open("data.csv", "w", newline="", encoding="utf-8") as f:
    writer = csv.writer(f)
    writer.writerows(data)

# CSVファイルの読み込み
with open("data.csv", "r", encoding="utf-8") as f:
    reader = csv.reader(f)
    result = []
    for row in reader:
        result.append(row)

print(result)

説明

  • ファイルをオープンするときにnewline=""を必ず指定する。これは、csvモジュール内で改行を出力するので、余計な改行が入らないようにするためである。
  • csv.writer: CSVファイルへの書き込みを行うwriterオブジェクトを返す。
  • writerows: 二重リストを一括でcsvファイルに書き込む。writerオブジェクトのメソッド。
  • csv.reader: CSVファイルの内容をリスト形式で読み込むreaderオブジェクト。
  • readerオブジェクトはfor文のなかで、csvから読み込んだ行を繰り返し変数に代入する。このように、繰り返し処理のできるオブジェクトは「イテラブル」と呼ばれる。
  • result.append(row): appendはリストのメソッドで、そのリストの最後に引数のデータを付け加える。

出力例:

[['都道府県', '人口', '面積', '企業数', '学校数'], ['東京都', '13929286', '2194', '104934', '1224'], ['大阪府', '8839469', '1904', '71283', '903']]

プログラム例2: 辞書形式での保存と読み込み

import csv

# データ
data = [
    {"都道府県": "東京都", "人口": 13929286, "面積": 2194, "企業数": 104934, "学校数": 1224},
    {"都道府県": "大阪府", "人口": 8839469, "面積": 1904, "企業数": 71283, "学校数": 903},
]

# CSVファイルへの保存
with open("data_dict.csv", "w", newline="", encoding="utf-8") as f:
    fieldnames = ["都道府県", "人口", "面積", "企業数", "学校数"]
    writer = csv.DictWriter(f, fieldnames=fieldnames)
    writer.writeheader()  # ヘッダー行を書き込む
    writer.writerows(data)

# CSVファイルの読み込み
with open("data_dict.csv", "r", encoding="utf-8") as f:
    reader = csv.DictReader(f)
    result = []
    for row in reader:
        result.append(row)

print(result)

説明

  • csv.DictWriter: 辞書形式のデータをCSVファイルに書き込むオブジェクトを生成する。csv.readerとの違いは後述
  • fieldnames: 列名(の順番)を指定するリスト。
  • writeheader: ヘッダー行をファイルに書き込む。
  • csv.DictReader: 辞書形式でCSVファイルを読み込むオブジェクトを生成。

出力例:

[{'都道府県': '東京都', '人口': '13929286', '面積': '2194', '企業数': '104934', '学校数': '1224'}, {'都道府県': '大阪府', '人口': '8839469', '面積': '1904', '企業数': '71283', '学校数': '903'}]

csv.readerとcsv.DictReaderの違い

この2つは「小文字だけ」と「大文字+小文字」の違いがありますが、その背景には次のような違いがあります。

  • csv.readerは関数である。そして、 readerオブジェクトを返す。
  • csv.DictReaderはクラスである。クラスなので大文字からはじまる(そしてキャメルケースである)。
  • csv.DictReader()はDictReaderのインスタンスを生成する。インスタンスの生成方法は以前のブログを参照。

両者とも、オブジェクト(インスタンス)を返すのは同じなのだが、その過程が、関数呼び出しなのか、インスタンス生成なのかが違います。 細かいことになりますが、大文字が使われたり、使われなかったりの理由は、そういうことなのです。

まとめ

本記事では、PythonCSVファイルを扱う方法について学びました。

  1. CSVとは何か

    • 表形式データを扱う軽量フォーマット。
  2. 表形式のデータのPythonでの実装方法

    • 二重リスト形式: シンプルだが、列名でのアクセスができない。
    • 辞書形式: 可読性が高いが、若干のオーバーヘッドあり。
  3. csvモジュールの使い方

    • csv.writercsv.DictWriterCSVファイルにデータを保存。
    • csv.readercsv.DictReaderでデータを読み込む。