Select Language

AI Technology Community

5.12、Python csvモジュール:csvファイルを処理する

CSVファイルは本質的にテキストファイルで、表形式のデータを保存するために使用されます。行内のセルはカンマで区切り、異なる行は改行文字で区切ります。以下は普通のCSVファイルの例で、2行2列の内容を持っています。

第一行第一列,第一行第二列
第二行第一列,第二行第二列


このCSVファイルをExcelで表示した結果は図1の通りです。


図1 普通のCSVファイル


もしセルの内容に「,」区切り文字が含まれている場合、そのセルの内容は二重引用符で囲まれます。以下のCSVファイルの内容は「,」区切り文字を含むセルの例です。

"包括,的单元",第一行第二列
第二行第一列,第二行第二列


注意してください、第一行第一列のセルは二重引用符で囲まれています。このファイルをExcelで表示した結果は図2の通りです。


図2 「,」区切り文字を含むセル


セルの内容が複数行にわたる場合も、そのセルの内容は二重引用符で囲まれます。例えば、以下のCSVファイルの第一行第一列のセルは複数行の内容を持っています。

"包含换行符的单元
第2行
第三行",第一行第二列
第二行第一列,第二行第二列

このファイルをExcelで表示した結果は図3の通りです。


図3 複数行の内容を含むセル


セルの内容に二重引用符が含まれている場合はどうでしょうか?やはり二重引用符で内容を囲み、内容中の二重引用符は連続した2つの二重引用符で表されます。例えば、以下のCSVファイルの第一行第一列のセルは「”」文字を含んでいます。


図4 二重引用符を含むセル


これらからわかるように、CSVファイルの形式は比較的シンプルで、「,」と「”」を使うことで、テキストのみの表形式データを完全に表現することができます。Pythonでは、テキストファイルを操作する方法を使わずにCSVファイルを処理することができます。多くのライブラリを使って直接セルの内容を操作できるので、CSVファイルの形式の詳細を気にする必要はありません。このセクションでは、CSVファイルを処理する一般的なモジュールであるcsvモジュールについて説明します。

csvモジュールはPythonの組み込みモジュールで、インストールする必要はなく、使用する前にインポートするだけです。インポート方法は以下の通りです。

import csv

CSVファイルに対する操作は主に2つあります。一つは読み込み、もう一つは書き出しです。まず、読み込みについて説明します。csvモジュールにはreaderクラスがあり、このクラスのインスタンスオブジェクトは反復可能です。つまり、for...in...文を使ってCSVファイルのすべての行を反復処理することができます。また、line_num属性があり、現在読み込んでいる行番号を表します。

以下は、図1に示すCSVファイルを例にした操作のデモです。

>>> import csv # csvモジュールをインポート
>>> reader_obj = csv.reader(open('demo1.csv', 'r', encoding="utf-8"))
>>> for line in reader_obj: # 各行に対する操作
...     print("line number: %d" % reader_obj.line_num) # 現在の行番号を表示
...     print("content: %s" % str(line)) # 現在の行の内容を表示
...     print("") # 改行を出力
... # forループの終了
line number: 1 # 行番号は1
content: ['第一行第一列', '第一行第二列'] # 内容はリスト
# 第6行の出力
line number: 2 # 行番号は2
content: ['第二行第一列', '第二行第二列'] # 第二行の内容

以下は、詐欺電話を探す例です。詐欺電話には、外に電話をかけるだけで、他の人からの電話を受け取らないという特徴があります。今、完全な通話記録を持っています。内容は図5の通りです。


図5 通話記録


この通話記録の第一列は発信者の電話番号、第二列は着信者の電話番号、第三列は通話開始時間、第四列は通話時間です。これらのデータを使って、詐欺電話番号を見つけたいと思います。すべての行を順番に読み込み、発信者番号のリストの中から、着信者番号のリストに含まれていない番号を探します。これらの番号が詐欺電話番号の可能性があります。

実装コードは以下の通りです。

import sys, csv
# 通話記録ファイルを開く
if sys.version_info.major == 3: # python3
    f = open("telephone.csv", "r", encoding="utf-8", newline="\n")
else: # Python 2
    f = open("telephone.csv", "r")
reader = csv.reader(f)
caller_list = [] # 発信者番号のリスト
callee_list = [] # 着信者番号のリスト、最初は空
for record in reader: # 各記録に対する処理
    # 第一行はヘッダーなので処理しない
    if reader.line_num == 1:
        continue
    caller_list.append(record[0]) # すべての発信番号を記録
    # すべての着信番号を記録
    callee_list.append(record[1])
caller_list = set(caller_list) # 重複する発信番号を削除
f.close() # ファイルを閉じる
# 各発信番号に対して
for caller in caller_list: # 着信されたことがない場合は、詐欺番号としてマーク
    if caller not in callee_list:
        print(caller, "is Cheat Telephone Number")

実行後の出力は以下の通りです。

$ python cheatTel1.py
13243767000 is Cheat Telephone Number


次に、データをCSVファイルに出力する方法について説明します。csvモジュールにはwriterクラスがあり、writerow()とwriterows()の2つのインターフェース関数を提供しています。これらのインターフェース関数を使って、リストデータをCSVファイルに出力することができます。

以下は、writerow()を使ってCSVファイルを生成する簡単な例です。

import csv
csv_writer_obj = csv.writer(open("writeDemo1.csv", "w"))
csv_writer_obj.writerow(("a", "b", 12, 24.6))

出力ファイルwriteDemo1.csvの内容をExcelで表示した結果は図6の通りです。


図6 writeDemo1.csvファイルの内容


出力する際に、各行の列数が同じである必要はありません。例えば、以下のコードは3行を出力し、各行の列数はそれぞれ4、2、3です。

import csv
csv_writer_obj = csv.writer(open("writeDemo2.csv", "w"))
csv_writer_obj.writerow(("a", "b", 12, 24.6))
csv_writer_obj.writerow(("c", "d"))
csv_writer_obj.writerow(("e", "", "1"))

出力されたCSVファイルの内容は図7の通りです。


図7 writeDemo2.csvファイルの内容


もう一つのインターフェース関数はwriterows()です。名前の通り、この関数は一度に複数行を書き込むことができます。以下の例は、リストをCSVファイルに書き込む例です。

import csv
data = [ # リスト、各要素は一行を表す
    ["a", "b", "c"],
    ["d", "e", "f"],
]
csv_writer_obj = csv.writer(open("writeDemo3.csv", "w"))
csv_writer_obj.writerows(data)

出力されたCSVファイルの内容は図8の通りです。


図8 writeDemo3.csvの内容


post
  • 14

    item of content
データを長期的に保存したい場合、最も簡単な方法はデータをディスクファイルに書き込むことです。これにより、プログラムを終了した後でも処理結果は長期的に有効です。
大規模ソフトウェアプロジェクトでは、ファイル操作は避けられません。この章では、普通のテキストファイルとバイナリファイルの操作方法について説明します。具体的には、ファイルを開く方法、ファイルの読み書き、ファイルモード、および with 文の使用方法などを含みます。