(学習ログ)Python006:複数CSVの結合と売上集計の基本フロー
1. はじめに
-
この記事の目的
複数のCSVファイルを読み込み、縦方向の結合(concat)、キーに基づく横方向の結合(merge)、そして列演算・合計値の算出までを学びます。 -
この記事の概要
サンプルコードを行(またはブロック)単位で解説し、初心者がつまずきやすい「列指定の二重角括弧」やmergeの考え方、確認に便利なメソッド(head/info/shape/isnaなど)を紹介します。
2. サンプルコード
コード全文
import pandas as pd
sample_transaction1 = pd.read_csv('001_サンプル/sample_transaction_data1.csv')
sample_transaction2 = pd.read_csv('001_サンプル/sample_transaction_data2.csv')
sample_transaction = pd.concat([sample_transaction1, sample_transaction2], ignore_index=True)
sample_transaction_detail1 = pd.read_csv('001_サンプル/sample_transaction_detail1.csv')
sample_transaction_detail2 = pd.read_csv('001_サンプル/sample_transaction_detail2.csv')
sample_transaction_detail = pd.concat([sample_transaction_detail1, sample_transaction_detail2], ignore_index=True)
sample_join_data = pd.merge(sample_transaction_detail, sample_transaction[["transaction_id", "payment_date", "customer_id"]], on='transaction_id', how="left")
sample_file = pd.read_csv('001_サンプル/sample_file.csv')
sample_join_data = pd.merge(sample_join_data, sample_file, on="customer_id", how="left")
sample_item_list = pd.read_csv('001_サンプル/sample_item_list.csv')
sample_join_data = pd.merge(sample_join_data, sample_item_list, on="item_id", how="left")
sample_join_data["price"] = sample_join_data["quantity"] * sample_join_data["item_price"]
print(sample_join_data["price"].sum())
print(sample_transaction["price"].sum())
行ごと・ブロックごとの簡潔な説明
-
import pandas as pd
→ 分析の定番ライブラリpandasを読み込みます。 -
pd.read_csv(...transaction_data1/2...)
→ 取引(ヘッダ:transaction_id,payment_date,customer_idなど想定)のCSVを2分割で読み込みます。 -
pd.concat([...], ignore_index=True)
→ 2つの取引テーブルを縦に結合し、連番の新しいインデックスを振ります。これで「全期間の取引」sample_transactionが完成。 -
pd.read_csv(...transaction_detail1/2...)とconcat
→ 明細(transaction_idごとのitem_idやquantityなど想定)も同様に縦結合し、sample_transaction_detailにまとめます。 -
pd.merge(sample_transaction_detail, sample_transaction[["transaction_id", "payment_date", "customer_id"]], on='transaction_id', how="left")
→ 明細に対して、取引のメタ情報(支払日・顧客ID)をtransaction_idで左結合。
ポイント:sample_transaction[[...]]の二重角括弧は「複数列をDataFrameのまま選ぶ」ため(後述)。 -
pd.read_csv(...sample_file.csv...)→merge(..., on="customer_id", how="left")
→ 顧客マスタを読み込み、customer_idで左結合。顧客の属性(例:氏名・区分など)を付与します。 -
pd.read_csv(...sample_item_list.csv...)→merge(..., on="item_id", how="left")
→ 商品マスタを読み込み、item_idで左結合。商品名や単価(item_price)を付与します。 -
sample_join_data["price"] = sample_join_data["quantity"] * sample_join_data["item_price"]
→ 行単位の売上金額(数量×単価)を新列priceに計算して格納。 -
print(sample_join_data["price"].sum())
→ 明細ベースで集計した総売上(計算列)を合計して出力。 -
print(sample_transaction["price"].sum())
→ もし取引テーブル側に取引合計price列があるなら、その合計値も出力(突合せチェックに有用)。
実行結果例
例:
1254300
1254300
上2行はそれぞれ
1行目:明細から計算した総売上(合計)
2行目:取引テーブルに既に存在するprice合計(同額だと突合せクリア)
となります。両者が一致すれば、明細→取引の整合が取れているサインです。
3. エラーと確認のポイント
-
代表的なエラー文と対処
-
KeyError: 'transaction_id'/KeyError: 'customer_id'など
原因:CSV側のカラム名が想定と違う、あるいは全角半角・大小文字が異なる。
対処:読み込み直後にカラムを確認し、必要ならリネーム。
print(sample_transaction.columns) print(sample_transaction_detail.columns) # 例:列名を正規化 sample_transaction.columns = sample_transaction.columns.str.strip().str.lower()-
ValueError: You are trying to merge on object and int64 columns
原因:結合キーの型不一致(例:customer_idが片方は文字列、片方は数値)。
対処:読み込み時にdtypeを揃える、またはastypeで統一。
sample_transaction = pd.read_csv(..., dtype={"customer_id": "string", "transaction_id": "string"}) sample_transaction_detail["transaction_id"] = sample_transaction_detail["transaction_id"].astype("string")-
ParserError(CSVの区切りやエンコーディング起因)
原因:区切り文字・引用符・文字コードの不一致。
対処:encoding="utf-8-sig"やsep=";"の指定、quotecharの調整など。
pd.read_csv(path, encoding="utf-8-sig") # BOM付きCSV対策の一例 -
よく使う確認メソッドや出力例
最低限、以下を実施すると安心です。
- 形状・件数の確認(件数の増減を追う)
sample_transaction.shape # 例: (1200, 6)
sample_transaction_detail.shape# 例: (3400, 5)
sample_join_data.shape # 例: (3400, 12)
- 先頭・型・概要の確認
sample_join_data.head(3)
sample_join_data.info()
sample_join_data.dtypes
- 欠損値の把握(結合ミス検知)
sample_join_data.isna().sum().sort_values(ascending=False)
# 例: customer_name 10
# item_price 3
# → キー漏れやマスタ未整備の可能性
- キーの重複や一意性の確認(期待に応じて)
sample_transaction["transaction_id"].duplicated().sum() # 0が理想(一意)
sample_item_list["item_id"].duplicated().sum()
-
mergeの検証(想定外の重複結合を検出)
pd.merge(
sample_transaction_detail,
sample_transaction[["transaction_id", "payment_date", "customer_id"]],
on="transaction_id",
how="left",
validate="m:1" # 明細:取引 = 多対1 を期待
)
- 列選択の二重角括弧について(今回の重要ポイント)
sample_transaction[["transaction_id", "payment_date", "customer_id"]]のように二重角括弧を使うと、複数列をDataFrameとして選択できます。
一方、sample_transaction["transaction_id"](一重角括弧)はSeries(1列) になり、mergeに渡すとキーや引数の想定と合わない場合があります。結合相手にはDataFrameを渡すのが安全です。
4. まとめ
-
できるようになったこと(3点)
- 複数CSVを縦結合(
concat) し、期間や分割ファイルを1つの表にまとめられる。 - 外部キーに基づく横結合(
merge) で、「明細+取引+顧客+商品」の多段ジョインが組める。 - 計算列の追加(
quantity * item_price)と合計の比較により、突合せチェックまで行える。
- 複数CSVを縦結合(
Discussion