カラムAとカラムBに含まれる文字数を比較する python スクリプトを作成してみた
こんにちは!よしななです。
今回は、カラムAとカラムBをに含まれる文字数を比較する python スクリプトを作成し実行したので、備忘録としてブログに残します。
目次
- 実現したいこと
- 対象環境
- 事前準備
- フォルダ構成
- 仮想環境の立ち上げ
- ライブラリのインストール
- 実行したスクリプト
- スクリプトの説明
- 関数:longest_match_length について
- 関数:process_csv について
- 実行結果
- まとめ
実現したいこと
カラムAとカラムBにそれぞれ含まれる文字列を比較し、一致する文字列をカウントし返す処理をしたい。
〇例1:
文字列A:綺麗な沖縄の海~フェリーに乗って夏の旅~
文字列B:綺麗な沖縄の空
→"綺麗な沖縄の"までが一致するため、6を返す処理
〇例2:
文字列A:吾輩は猫である
文字列B:青空文庫
→一致する文字列はないため、0を返す処理
〇スクリプトの流れ
- 文字列A、文字列Bが入った.csvを読み込み
- 文字列A、文字列Bを比較し一致する文字列をカウントする
- 結果を.csvに出力する
という流れでスクリプトを作成してみます。
対象環境
本記事で実行した対象環境は以下となります。
- OS
- windows11
- エディタ
- VSCode
事前準備
フォルダ構成
本記事でのフォルダ構成は以下となります。
polars_test
フォルダを作成し、.py を以下の通り配置します。
仮想環境の立ち上げ
.py を配置したら、仮想環境(.venv)を立ち上げます。
https://dev.classmethod.jp/articles/venv-jupyternotebook/#toc-2 を参照し、.venv 環境を作成します。
次に.venv/Script/activate
を PowerShell で実行し、.venv 環境を起動します。
.venv/Scripts/activate
ライブラリのインストール
venv 環境を起動したら、polars のインストールを行います。
venv 環境が起動している状態で、pip install polars
を実行します。
venv 環境内にpolars
ライブラリがインストールされました。
pip polars install
スクリプトを作成
事前準備が完了したら、polars_test.py
スクリプトを作成します。
作成したスクリプトは以下となります。
import polars as pl
from difflib import SequenceMatcher
def longest_match_length(a: str, b: str) -> int:
return SequenceMatcher(None, a, b).find_longest_match(0, len(a), 0, len(b)).size
def process_csv(input_path: str, output_path: str) -> None:
try:
# CSVファイルの読み込み
df = pl.read_csv(input_path, infer_schema_length=0)
# カラム間の比較を行い、新しいカラムに一致する最長の文字列の長さを格納
df = df.with_columns(
pl.struct(pl.col('stringa'), pl.col('stringb'))
.map_elements(lambda x: longest_match_length(str(x['stringa']), str(x['stringb'])))
.alias('Matching_Length')
)
# 結果を新しいCSVファイルに保存
df.write_csv(output_path)
print(f"処理が完了しました。結果は {output_path} に保存されました。")
except Exception as e:
print(f"エラーが発生しました: {e}")
if __name__ == "__main__":
INPUT_PATH = '文字列を比較したい .csv が格納されたパス名'
OUTPUT_PATH = '出力結果先'
process_csv(INPUT_PATH, OUTPUT_PATH)
スクリプトの説明
関数:longest_match_length について
こちらの関数は、2つの文字列a
とb
を入力として受け取り、SequenceMatcher
クラスを使用して、a
とb
の文字列を比較しています。
find_longest_match
メソッドを使用して、文字列a
とb
内で文字が一致する部分を見つけた後、見つかった最長一致部分の長さを返す関数となります。
関数:process_csv について
CSV 読み込み
polars のread_csv
を使用し、csv の中身をデータフレームとして読み込みします。
カラム間の比較とカラムの追加
ここでは作成した関数:longest_match_length
を使用し、カラム間の比較を行い、新しいカラムに一致する最長の文字列の長さを追加する処理を行っています。
- DataFrame の
stringa
とstringb
カラムを選択します。
pl.struct
を使用し、stringa
カラムとstringb
カラムを構造体として選択します。- https://docs.pola.rs/api/python/stable/reference/expressions/api/polars.struct.html
- 各行の
stringa
とstringb
の値をlongest_match_length
関数に渡して処理します。
- 各行に対し、
map_elements
、lambda
を使用してlongest_match_length
関数を適用する - https://docs.pola.rs/api/python/stable/reference/expressions/api/polars.Expr.map_elements.html
- 処理結果を新しいカラム
Matching_Length
として追加します。
csv書き出し
polars のwrite_csv
を使用し、データフレームを csv に書き出します。
実行結果
実行前
実行前のファイルは以下の通りです。
実行後
スクリプトの実行後、以下の通り .csv ファイルが出力され、文字列を比較した数が返っていることを確認しました。
以上で、「カラムAとカラムBに含まれる文字数を比較する python スクリプトを作成してみた」は以上となります。
まとめ
map_elements
について、今回は2行のみのため処理速度について遅さは感じなかったのですが、csv の行数が多いと処理速度が遅くなったり…といったことがあるそうです。
次回以降の記事で、データ量が増えた場合の書き方についても調べたいなと思いました。
ここまで読んでいただき、ありがとうございました!