【Pandas文字列操作】区切り文字・正規表現で文字列を分割して複数列に分ける方法 str.split()
データ分析において、一つの文字列列の中に複数の情報が混在していることはよくあります。例えば、「名前,年齢,性別」のようなカンマ区切りの文字列や、「SKU-色コード-サイズ」のようなハイフン区切りの商品IDなどです。Pandasの強力なstr.split()メソッドを使えば、このような文字列を区切り文字や正規表現で分割し、DataFrameの複数の新しい列として展開することができます。この記事では、str.split()の基本的な使い方から、知っておくと便利な応用例まで、短いサンプルコードと丁寧な解説を交えてご紹介します。
なぜ文字列を分割して複数列にするのか?
文字列を分割して複数の列にする主な理由は以下の通りです。
-
データの正規化: 構造化されていないデータを、分析しやすい形式に整理します。
-
特徴量エンジニアリング: 既存の文字列データから、個別の意味を持つ新しい特徴量(列)を抽出します。
-
フィルタリング・集計: 分割された個々の情報に基づいて、データをフィルタリングしたり、集計したりすることが容易になります。
-
可読性の向上: 一つの文字列に複数の情報が詰まっているよりも、それぞれの情報が独立した列になっている方が、データセット全体の可読性が向上します。
str.split()の基本的な使い方
str.split()メソッドは、Series(文字列型の列)に対して適用し、指定した区切り文字で文字列を分割します。
カンマ区切りで文字列を分割する
最も一般的な使い方で、カンマなど単一の区切り文字で文字列を分割します。
import pandas as pd
# サンプルDataFrameの作成
df = pd.DataFrame({
'商品情報': ['りんご,赤,100', 'みかん,オレンジ,120', 'バナナ,黄,80'],
'ユーザーID': ['user_001_A', 'user_002_B', 'user_003_C']
})
print("オリジナルDataFrame:\n", df)
# '商品情報'列をカンマで分割し、新しい列として展開
df[['商品名', '色', '価格']] = df['商品情報'].str.split(',', expand=True)
print("\n'商品情報'列を分割後:\n", df)
解説:
-
df['商品情報'].str.split(','): ‘商品情報’列の各文字列をカンマ,で分割します。この時点では、リストのSeriesが返されます。 -
expand=True: これが重要です。分割されたリストの要素を、それぞれ新しい列としてDataFrameに展開するようPandasに指示します。 -
df[['商品名', '色', '価格']] = ...: 新しく生成された列に、適切な列名を割り当てます。
空白文字で文字列を分割する
デフォルトでは、str.split()は引数を指定しない場合、任意の連続する空白文字で分割し、空の文字列は結果に含めません。これは複数のスペースで区切られたデータに便利です。
df_space = pd.DataFrame({'Text': ['Hello world', ' Python Pandas ']})
print("\n空白区切りオリジナルDataFrame:\n", df_space)
# 空白文字で分割(デフォルト動作)
df_space[['Word1', 'Word2']] = df_space['Text'].str.split(expand=True)
print("\n空白文字で分割後:\n", df_space)
解説:
2行目の’ Python Pandas ‘は、前後のスペースや間の複数のスペースが適切に処理され、’Python’と’Pandas’に分割されています。
str.split()の応用的な使い方
str.split()は、より複雑な分割ニーズに対応するための引数も持っています。
分割回数を制限する: n引数
n引数に整数を指定することで、文字列を分割する回数を制限できます。これにより、最初のN個の区切り文字までで分割し、残りの部分は結合されたままになります。
df_limit = pd.DataFrame({
'Path': ['folder1/subfolderA/file1.txt', 'folder2/file2.csv']
})
print("\nパス情報オリジナルDataFrame:\n", df_limit)
# 最初の1回だけ'/'で分割
df_limit[['Root', 'Rest']] = df_limit['Path'].str.split('/', n=1, expand=True)
print("\n最初の1回だけ分割後:\n", df_limit)
解説:
n=1とすることで、最初の’/’で一度だけ文字列が分割され、それ以降の’/’はそのまま残っています。これはパスのルートディレクトリと残りを分けたい場合などに便利です。
正規表現で文字列を分割する
str.split()は、区切り文字として正規表現を受け入れることができます。これにより、より柔軟なパターンでの分割が可能になります。
df_regex = pd.DataFrame({
'Data': ['ID:123|Name:Alice', 'ID:456|Name:Bob|Age:30']
})
print("\n正規表現適用前DataFrame:\n", df_regex)
# 'ID:', '|Name:', '|Age:' で分割 (正規表現)
# 空文字列が生成される場合があるので注意
df_regex_split = df_regex['Data'].str.split(r'ID:|\|Name:|\|Age:', expand=True)
print("\n正規表現で分割後DataFrame:\n", df_regex_split)
解説:
-
r'ID:|\|Name:|\|Age:': この正規表現は、'ID:'または'|Name:'または'|Age:'のいずれかのパターンで文字列を分割します。|は正規表現の特殊文字なのでエスケープ(\|)が必要です。 -
この例では、正規表現のパターンの位置によっては空文字列の列が生成される場合があります。適切な列を選択したり、
dropna(axis=1, how='all')で空の列を削除したりすることが必要になる場合があります。
欠損値(NaN)の扱い
分割対象の列に欠損値(NaN)が含まれている場合、str.split()はデフォルトでその行の分割結果もNaNとします。
import numpy as np
df_nan_split = pd.DataFrame({'Info': ['A,B', np.nan, 'C,D']})
print("\nNaNを含むオリジナルDataFrame:\n", df_nan_split)
df_nan_split[['Col1', 'Col2']] = df_nan_split['Info'].str.split(',', expand=True)
print("\nNaNを含む列を分割後:\n", df_nan_split)
解説:
インデックス1のnp.nanは、分割結果もnp.nanとして保持されています。これは望ましい挙動であることが多いですが、必要であればfillna()などでNaNを事前に処理することも可能です。
まとめ
Pandasのstr.split()メソッドは、DataFrameの文字列列を区切り文字や正規表現で分割し、複数の新しい列として展開するための非常に強力で柔軟なツールです。expand=Trueで効率的に列を展開し、n引数で分割回数を制限したり、正規表現で複雑なパターンに対応したりすることができます。これらのstr.split()のテクニックをマスターすることで、データのクレンジングや特徴量エンジニアリングを格段に効率化し、より分析しやすいデータセットを構築できるようになるでしょう。

