search_cif_db_tkcif.py ドキュメント
このドキュメントは、結晶構造情報ファイル(CIF)を再帰的に検索し、SQLite3データベースを作成・管理するPythonスクリプト search_cif_db_tkcif.py について説明します。作成されたデータベースを使用して、組成から構造データを検索できます。
1. 概要
search_cif_db_tkcif.py は、指定されたルートディレクトリ以下のCIFファイルを読み込み、その組成や結晶学的情報を抽出してSQLite3データベースにインデックス化します。一度データベースが構築されれば、ファイルシステムを再度スキャンすることなく、高速に組成に基づいた検索を実行できます。
主な機能は以下の3つのモードです。
index: CIFファイルをスキャンし、データベースを構築または更新します。search: データベースに登録されたデータに対して、指定された組成で検索を実行します。info: データベースの統計情報を表示します。
CIFファイルの読み込みには tkcif.tkcif_reader.read_structure() 関数を、組成の処理には pymatgen.core.Composition クラスを使用しています。
2. インストール
このスクリプトは、以下の非標準ライブラリに依存しています。
pymatgentkcif
pymatgen は以下のコマンドでインストールできます。
pip install pymatgen
tkcif のインストール方法はコードからは確認できませんが、pymatgen と同様に pip でインストールできる可能性があります。
# 例:
# pip install tkcif
必要なライブラリがインストールされていない場合、スクリプトはエラーメッセージを表示して終了します。
3. 使い方
3.1. コマンドライン引数
search_cif_db_tkcif.py は以下のコマンドライン引数をサポートします。
--mode型:
strデフォルト:
search選択肢:
index,search,info実行モードを指定します。
--root型:
strデフォルト:
.indexモードで使用され、CIFファイルを検索するルートディレクトリを指定します。
--db型:
strデフォルト:
cif_index.sqlite使用するSQLite3データベースファイルのパスを指定します。
--pattern型:
strデフォルト:
*.cifindexモードで使用され、検索するCIFファイルのパターンを指定します。
--formula型:
strデフォルト:
""searchモードで使用され、検索対象の化学式を指定します。
--match型:
strデフォルト:
exact選択肢:
exact,elements,containssearchモードで使用され、化学式のマッチング方法を指定します。exact: 還元組成が完全に一致するものを検索します(例:BaTiO3とTiBaO3はどちらもBaTiO3に正規化され、一致とみなされます)。elements: 元素集合が完全に一致するものを検索します(例:Ba-Ti-O系のみ)。contains: 指定された元素集合の部分集合を許します(例:BaTiO3で検索した場合、Ba,Ti,O,BaO,TiO2,BaTiO3などがヒットします)。
--source-db型:
strデフォルト:
""searchモードで使用され、データベースのsource_db列でフィルタリングするための値を指定します(例:cod,tcod,pcod)。空の場合、全てのデータベースを検索します。
--store-errors型:
intデフォルト:
1選択肢:
0,1indexモードで使用され、CIFファイルの読み込みエラーが発生した場合に、そのエラー情報をデータベースに記録するかどうかを指定します(1で記録、0で記録しない)。
--json型:
intデフォルト:
0選択肢:
0,1searchモードで使用され、検索結果をJSON形式で標準出力に出力するかどうかを指定します(1でJSON出力、0で可読形式)。
--limit型:
intデフォルト:
100searchモードで使用され、検索結果の最大表示数を指定します。
3.2. 使用例
# ./COD ディレクトリ以下の CIF ファイルをスキャンし、cif_index.sqlite にインデックスを作成
python search_cif_db_tkcif.py --mode index --root ./COD --db cif_index.sqlite
# cif_index.sqlite データベースの統計情報を表示
python search_cif_db_tkcif.py --mode info --db cif_index.sqlite
# cif_index.sqlite から BaTiO3 の還元組成と完全に一致する構造を検索
python search_cif_db_tkcif.py --mode search --db cif_index.sqlite --formula BaTiO3
# cif_index.sqlite から TiBaO3 の還元組成と完全に一致する構造を検索(BaTiO3 と同じ結果になる)
python search_cif_db_tkcif.py --mode search --db cif_index.sqlite --formula TiBaO3 --match exact
# cif_index.sqlite から Ba, Ti, O の元素集合が完全に一致する構造を検索
python search_cif_db_tkcif.py --mode search --db cif_index.sqlite --formula BaTiO3 --match elements
# cif_index.sqlite から Ba, Ti, O を含む元素集合を持つ構造を検索(Ba, Ti, O の部分集合もヒット)
python search_cif_db_tkcif.py --mode search --db cif_index.sqlite --formula BaTiO3 --match contains
4. プログラムの説明
4.1. 全体概要
スクリプトのエントリーポイントは main() 関数です。この関数はコマンドライン引数を解析し、指定された --mode に応じて以下のいずれかの主要な処理関数を呼び出します。
build_index():--mode indexが指定された場合。search_by_formula():--mode searchが指定された場合。show_info():--mode infoが指定された場合。
4.2. 主要関数
guess_db_name(path: Path) -> strCIFファイルのパスから、それが属するデータベース名(例:
cod,tcod,pcod)を推測します。
guess_material_id(path: Path) -> strCIFファイルのファイル名から、数字の材料IDを推測します(例:
1234567.cifから1234567)。
composition_to_sorted_json(comp: Composition) -> strpymatgen.core.Compositionオブジェクトを、元素名でソートされたJSON文字列に変換します。
normalize_formula(formula: str) -> str与えられた化学式を
pymatgen.core.Compositionを使用して標準化し、還元式を返します。
composition_info_from_structure(path: Path) -> dict[str, Any]指定されたCIFファイルから結晶構造を読み込み、組成、還元式、匿名化された式、元素集合、サイト数、空間群情報、セルパラメータ、体積、密度など、データベースに格納するメタデータを抽出します。
get_existing_columns(conn: sqlite3.Connection, table_name: str) -> set[str]指定されたSQLite3データベース接続とテーブル名から、既存の列名セットを取得します。
create_schema(conn: sqlite3.Connection) -> Nonecif_indexテーブルのスキーマを作成します。テーブルが存在しない場合は新規作成し、既存のテーブルには不足している列を追加してスキーマを更新します。また、検索性能向上のためのインデックスも作成します。
upsert_record(conn: sqlite3.Connection, rec: dict[str, Any]) -> None指定されたレコード(辞書)を
cif_indexテーブルに挿入または更新(既存の場合は置換)します。
build_index(root: Path, db_path: Path, pattern: str = "*.cif", store_errors: int = 1, commit_interval: int = 200) -> None--mode indexの際に呼び出されます。指定されたルートディレクトリ以下を再帰的に検索し、パターンに一致するCIFファイルごとにcomposition_info_from_structure()を呼び出してデータを抽出し、データベースにインデックス化します。エラーが発生したCIFファイルは、オプションでエラー情報とともに記録されます。
make_subset_condition_for_contains(target_elements: list[str]) -> tuple[str, list[Any]]searchモードの--match containsオプションのために、SQLiteのLIKE句を用いたSQL条件とパラメータを作成します。
search_by_formula(db_path: Path, formula: str, source_db: str = "", match: str = "exact", limit: int = 100, output_json: int = 0) -> None--mode searchの際に呼び出されます。指定された化学式とマッチングモードに基づいてデータベースを検索し、結果を標準出力に表示します。オプションでJSON形式での出力も可能です。
show_info(db_path: Path) -> None--mode infoの際に呼び出されます。データベースの全体的な統計情報、ステータスごとのカウント、source_dbおよびbackendごとのカウントなどを標準出力に表示します。
main() -> Noneスクリプトのエントリーポイント。コマンドライン引数を解析し、適切な処理関数を呼び出します。
4.3. 入出力
4.3.1. 入力
CIFファイル:
--mode indexの際、--rootで指定されたディレクトリ以下の--patternに一致するすべてのCIFファイルが入力として読み込まれます。SQLite3データベースファイル:
--db引数で指定されたSQLite3データベースファイルが読み込まれ、indexモードでは書き込み、searchおよびinfoモードでは読み込みのためにアクセスされます。コマンドライン引数: スクリプトの動作を制御するために、上記「3.1. コマンドライン引数」で説明された引数が入力として与えられます。
4.3.2. 出力
SQLite3データベースファイル:
--mode indexが実行されると、--dbで指定されたパスにSQLite3データベースファイルが作成または更新されます。このファイルには、スキャンされたCIFファイルのメタデータが格納されます。標準出力:
--mode index: インデックス作成の進捗状況、エラーメッセージ、完了時のサマリー(処理されたファイル数、エラー数、バックエンドの集計など)が出力されます。--mode search:--json 0(デフォルト) の場合、検索クエリの詳細、ヒット数、および各結果の整形された情報(ソースDB、材料ID、還元式、空間群、セルパラメータ、体積など)が出力されます。--json 1の場合、検索結果がJSON形式で標準出力に出力されます。
--mode info: データベースの統計情報(ステータスごとの総数、source_dbやbackendごとの集計など)が出力されます。
エラー出力:
pymatgenまたはtkcifのインポートに失敗した場合、関連するエラーメッセージとトレースバックが標準エラー出力または標準出力に出力され、スクリプトは終了します。CIFファイルの読み込みエラーは、indexモード時に標準出力に[ERROR]プレフィックス付きで出力されます。
4.4. データモデル (SQLiteスキーマ)
データベース cif_index.sqlite (または --db で指定された名前) には、cif_index という名前のテーブルが作成されます。このテーブルのスキーマは以下の通りです。
id INTEGER PRIMARY KEY AUTOINCREMENTsource_db TEXT: 推定されたデータベース名(例:cod,tcod)。material_id TEXT: 推定された材料ID。cif_path TEXT UNIQUE: CIFファイルの絶対パス。formula TEXT: 元の化学式。reduced_formula TEXT: 還元された化学式。anonymous_formula TEXT: 匿名化された化学式。composition_json TEXT: 組成をソートされたJSON形式で表現した文字列。elements TEXT: 含まれる元素のカンマ区切りリスト(例:Ba,O,Ti)。nelements INTEGER: 含まれる元素の種類数。nsites INTEGER: 構造中のサイト数。sg_symbol TEXT: 空間群記号。sg_number INTEGER: 空間群番号。volume REAL: セル体積(Å^3)。volume_per_atom REAL: 1原子あたりのセル体積(Å^3)。density REAL: 密度(g/cm^3)。a REAL: 格子定数a。b REAL: 格子定数b。c REAL: 格子定数c。alpha REAL: 格子角alpha。beta REAL: 格子角beta。gamma REAL: 格子角gamma。backend TEXT: 構造解析に使用されたバックエンド(例:pymatgen,ase)。normalized INTEGER: 構造が正規化されたかどうかを示すフラグ(1なら正規化済み、0なら未正規化)。status TEXT: レコードの処理ステータス(okまたはerror)。error TEXT: 処理エラーが発生した場合のエラーメッセージ。
以下のインデックスが作成され、検索性能が向上しています。
idx_formula(reduced_formula)idx_elements(elements)idx_source_db(source_db)idx_backend(backend)idx_sg_number(sg_number)idx_volume_per_atom(volume_per_atom)
5. 依存ライブラリ
このスクリプトは、以下のPythonライブラリを使用しています。
5.1. 標準ライブラリ
argparse: コマンドライン引数の解析に使用されます。json: 組成情報をJSON形式に変換したり、JSON形式で検索結果を出力したりするのに使用されます。re: 正規表現による文字列操作(材料IDの推測など)に使用されます。sqlite3: SQLite3データベースの操作(接続、スキーマ作成、データの挿入・検索など)に使用されます。sys: システム固有のパラメータや関数(プログラムの終了など)に使用されます。traceback: エラー発生時のトレースバック情報の取得・表示に使用されます。warnings: 警告メッセージのフィルタリング(pymatgen/ASEの警告抑制)に使用されます。pathlib.Path: ファイルパスをオブジェクト指向で操作するのに使用されます。typing: 型ヒント(Any,list,dictなど)に使用されます。
5.2. 非標準ライブラリ
pymatgen(具体的にはpymatgen.core.Composition)化学式の解析、標準化、組成情報の抽出に使用されます。
tkcif(具体的にはtkcif.tkcif_reader.read_structure)CIFファイルから結晶構造データを読み込み、
pymatgen互換のStructureオブジェクトを生成するのに使用されます。
6. ライセンス
このプログラムのライセンス情報はコードからは確認できません。
7. 著者
このプログラムの著者情報はコードからは確認できません。