7. オブジェクトデータベースの基本操作とデータ分析
【概要】
本章では,Python オブジェクトをそのまま永続化できるオブジェクト指向データベース ZODB の基本操作を学ぶ。トランザクション・コミット・アボートの考え方を理解し,ZODB へのデータ格納と永続化の確認,pandas を用いた CSV データの読み込みと格納,並べ替え,頻度分析,可視化までを,演習を通して順に確認する。
本章のコードは,Windows 上の Python でも Colab でも動作する。iris データセットは URL から取得する方式とし,Windows 固有のファイルパス指定を用いない。
【目次】
- データベーストランザクションの基礎概念
- ZODB データベースの基本操作
- 演習準備
- 演習の進め方
- 演習1.ZODB へのデータ格納と永続化の確認
- 演習2.pandas による CSV データの読み込みと ZODB への格納
- 演習3.データの並べ替え
- 演習4.頻度分析
- 演習5.データの可視化
【関連する外部ページ】
【サイト内の関連ページ】
データベーストランザクションの基礎概念
トランザクション
データベースにおける一連の処理をまとめた作業単位である。データの一貫性を保つための概念である。
コミット命令(commit)
トランザクションで実行した一連のデータベース操作を確定し,その結果をデータベースに永続的に反映させる命令である。
アボート命令(abort)
トランザクションで実行した一連のデータベース操作を取り消し,トランザクション開始前の状態に戻す命令である。
ZODB データベースの基本操作
ZODB の概要
ZODB(Zope Object Database)は,Python オブジェクトを直接永続化(プログラム終了後もデータを保持すること)できるオブジェクト指向データベースである。Python の辞書やリスト,自作クラスのインスタンスなどを,変換処理を介さずにそのままディスクに保存できる。
ZODB では次の3つのモジュールを使用する。
ZODB.FileStorage:データをファイルに保存するためのストレージを提供する。ZODB:データベースインスタンス(DBクラス)を管理する。transaction:トランザクション(コミット・アボート)を制御する。
データベースへの接続とルートオブジェクトの取得
データベースへの接続は次の手順で行う。FileStorage でファイルベースのストレージを作成し,DB でデータベースインスタンスを生成する。db.open() で接続を開き,conn.root() でルートオブジェクト(データの格納先となる最上位オブジェクト)を取得する。
import ZODB
import ZODB.FileStorage
import transaction
storage = ZODB.FileStorage.FileStorage('hoge.fs')
db = ZODB.DB(storage)
conn = db.open()
root = conn.root()
ルートオブジェクトの構造
ルートオブジェクトは PersistentMapping(永続化機能を備えたマッピングクラス)として実装されており,Python の辞書型と同様のインタフェースを持つ。キーと値のペアでデータを格納し,keys() メソッドで格納済みキーの一覧を取得できる。データベース新規作成時は空の状態で初期化される。
トランザクションのコミット
transaction.commit() を実行することで,メモリ上の変更内容をストレージに永続化する。コミットを行わずにプログラムを終了した場合,変更内容は失われる。
演習準備
この演習では Python を使用する。Python がインストールされていない場合は,下記の「Python 3.12 のインストール」を展開し,手順に従いインストールすること。続いて,下記の「必要なライブラリのインストール」を実施すること。
Python 3.12 のインストール
Pythonのインストールを行い、Pythonのプログラムを実行する環境を整える。扱う環境は、Windows搭載パソコンである。金子研究室では、Python 3.12.10を推奨する。
[Windows での Python 3.12 のインストール手順を見るには、ここをクリック]
Windows での Python 3.12 のインストール
以下のいずれかの方法でPython 3.12をインストールする。Pythonがインストール済みの場合、この手順は不要である。
方法 1:winget によるインストール
【インストールコマンドの実行方法】
管理者権限でコマンドプロンプトを起動する(手順:Windowsキーまたはスタートメニュー → cmd と入力 → 右クリック → 「管理者として実行」)。そして、コマンド全体をコマンドプロンプトにコピー&ペーストする。
--scope machine を指定することで、システム全体(全ユーザー向け)にインストールされる。このオプションの実行には管理者権限が必要である。インストール完了後、コマンドプロンプトを再起動するとPATHが反映される。
REM Python 3.12 をシステム領域にインストール
winget install --id Python.Python.3.12 -e --scope machine --silent --accept-source-agreements --accept-package-agreements --override "/quiet InstallAllUsers=1 PrependPath=1 Include_test=0 Include_pip=1 Include_launcher=1 InstallLauncherAllUsers=1 TargetDir=\"C:\Program Files\Python312\""
REM Python と Scripts を PATH 先頭に追加
powershell -NoProfile -Command "$p='C:\Program Files\Python312'; $s=\"$p\Scripts\"; $c=[Environment]::GetEnvironmentVariable('Path','Machine'); if((Test-Path $p) -and (';'+$c+';' -notlike \"*;$p;*\") -and (';'+$c+';' -notlike \"*;$s;*\")){[Environment]::SetEnvironmentVariable('Path',\"$p;$s;$c\",'Machine')}"
方法 2:インストーラーによるインストール
- Python公式サイト(https://www.python.org/downloads/)にアクセスし、「Download Python 3.x.x」ボタンからWindows用インストーラーをダウンロードする。
- ダウンロードしたインストーラーを実行する。
- 初期画面の下部に表示される「Add python.exe to PATH」にチェックを入れてから「Customize installation」を選択する。このチェックを入れ忘れると、コマンドプロンプトから
pythonコマンドを実行できない。 - 「Install Python 3.xx for all users」にチェックを入れ、「Install」をクリックする。
インストールの確認
コマンドプロンプトで以下を実行する。
python --version
バージョン番号(例:Python 3.12.x)が表示されればインストール成功である。「'python' は、内部コマンドまたは外部コマンドとして認識されていません。」と表示される場合は、インストールが正常に完了していない。
必要なライブラリのインストール [クリックして展開]
管理者権限でコマンドプロンプトを起動する
(手順:Windowsキーまたはスタートメニュー → cmd と入力 → 右クリック → 「管理者として実行」)。
起動したコマンドプロンプトで以下を実行する。--no-user はユーザーディレクトリへのインストールを抑止し,システム全体(全ユーザー向け)にインストールするためのオプションである。Colab で実行する場合は --no-user を付けず,ノートブックのセル先頭に ! を付けて !pip install -U ZODB pandas matplotlib seaborn として実行する。
pip install -U --no-user ZODB pandas matplotlib seaborn
演習の進め方
各演習のコードを実行(メモ帳を用いる場合は a.py のようなファイル名で保存して実行)する。Colab で実行する場合は,各コードをそのままセルに貼り付けて実行する。コードのまとまった単位ごとに実行し,結果を確認しながら進める。
演習1.ZODB へのデータ格納と永続化の確認
手順
① 次のコードを実行(メモ帳を用いる場合は a.py のようなファイル名で保存して実行)する。ZODB に辞書型データを格納し,コミットする。
import ZODB
import ZODB.FileStorage
import transaction
storage = ZODB.FileStorage.FileStorage('hoge.fs')
db = ZODB.DB(storage)
conn = db.open()
root = conn.root()
print('格納前のキー一覧:', list(root.keys()))
root['sample'] = {'name': 'Alice', 'age': 25}
transaction.commit()
print('格納後のキー一覧:', list(root.keys()))
print('格納されたデータ:', root['sample'])
conn.close()
db.close()
② プログラムを終了した後,再度同じプログラムを実行する。「格納前のキー一覧」に 'sample' が含まれていることを確認する。
ヒント
- 1回目の実行では「格納前のキー一覧」は空であるが,2回目以降は前回コミットした内容が残っている。
conn.close()とdb.close()でデータベースへの接続を閉じる。
考察ポイント
- プログラムを終了しても格納したデータが消えないことから,永続化が機能していることを読み取る。
- 1回目と2回目の「格納前のキー一覧」の違いから,コミットがデータをディスクに反映する役割を担っていることを確認する。
演習2.pandas による CSV データの読み込みと ZODB への格納
手順
① 次のコードを実行(メモ帳を用いる場合は a.py のようなファイル名で保存して実行)する。iris データセットを URL から読み込み,ZODB に格納する。
import ZODB
import ZODB.FileStorage
import transaction
import pandas as pd
storage = ZODB.FileStorage.FileStorage('hoge.fs')
db = ZODB.DB(storage)
conn = db.open()
root = conn.root()
URL = 'https://raw.githubusercontent.com/mwaskom/seaborn-data/master/iris.csv'
iris = pd.read_csv(URL, header=0)
root['iris_data'] = iris
transaction.commit()
print(root['iris_data'].head())
conn.close()
db.close()
ヒント
pd.read_csvは URL を引数に指定して,Web 上の CSV ファイルをデータフレーム(表形式のデータ構造)として直接読み込める。header=0はファイルの1行目を列名として扱う指定である。head()はデータフレームの先頭5行を表示するメソッドである。
考察ポイント
- CSV ファイルの内容がデータフレームとして読み込まれ,列名と各行のデータが構造化されていることを確認する。
- pandas のデータフレームが ZODB にそのまま格納できることを確認する(オブジェクト指向データベースの特徴)。
演習3.データの並べ替え
手順
① 次のコードを実行(メモ帳を用いる場合は a.py のようなファイル名で保存して実行)する。sepal_length 列を基準に昇順・降順で並べ替える。
import ZODB
import ZODB.FileStorage
storage = ZODB.FileStorage.FileStorage('hoge.fs')
db = ZODB.DB(storage)
conn = db.open()
root = conn.root()
print('昇順:')
print(root['iris_data'].sort_values(by='sepal_length').head())
print('降順:')
print(root['iris_data'].sort_values(by='sepal_length', ascending=False).head())
conn.close()
db.close()
ヒント
sort_valuesのby引数で並べ替えの基準列を指定する。ascending=Trueで昇順,ascending=Falseで降順となる(既定値はTrue)。
考察ポイント
- 昇順・降順の先頭5行を比較し,
sepal_lengthの最小値・最大値を持つ行が抽出されていることを確認する。 - 並べ替えの基準列以外の値も連動して並び替わることを確認する。
演習4.頻度分析
手順
① 次のコードを実行(メモ帳を用いる場合は a.py のようなファイル名で保存して実行)する。
import ZODB
import ZODB.FileStorage
storage = ZODB.FileStorage.FileStorage('hoge.fs')
db = ZODB.DB(storage)
conn = db.open()
root = conn.root()
print(root['iris_data']['sepal_length'].value_counts())
conn.close()
db.close()
ヒント
value_counts()は値ごとの出現回数を集計し,既定では出現回数の降順で表示する。root['iris_data']['sepal_length']でデータフレームから1列を取り出している。
考察ポイント
- どの値が最も多く出現しているかを確認する。
- 出現回数の分布から,データに偏りがあるかを読み取る。
演習5.データの可視化
手順
① 次のコードを実行(メモ帳を用いる場合は a.py のようなファイル名で保存して実行)する。Matplotlib による散布図と,Seaborn によるカテゴリ別散布図を表示する。
import ZODB
import ZODB.FileStorage
import matplotlib.pyplot as plt
import seaborn
storage = ZODB.FileStorage.FileStorage('hoge.fs')
db = ZODB.DB(storage)
conn = db.open()
root = conn.root()
plt.plot(root['iris_data']['sepal_length'], root['iris_data']['sepal_width'], 'o')
plt.xlabel('sepal_length')
plt.ylabel('sepal_width')
plt.show()
seaborn.lmplot(data=root['iris_data'], x='sepal_length', y='sepal_width',
fit_reg=False, hue='species')
plt.show()
conn.close()
db.close()
ヒント
plt.show()でグラフ描画ウィンドウが表示される(Colab ではセルの出力にインライン表示される)。Windows のウィンドウを閉じると次の処理に進む。'o'は円形マーカーの指定である。hue='species'はspecies列の値ごとに点の色を変える指定である。fit_reg=Falseは回帰直線を描画しない指定である(既定では描画される)。
考察ポイント
- Matplotlib の散布図から,
sepal_lengthとsepal_widthの関係性(正の相関,負の相関,または無相関)を読み取る。 - Seaborn のカテゴリ別散布図から,
speciesごとに点の分布が異なる領域に集まっているかを確認し,種の判別に有効な特徴量であるかを考察する。