- Day 19:正規表現で「文字列を賢く扱う」力を身につける
- 正規表現とreモジュールの基本
- 検索:文字列の中から「パターンに合う部分」を探す
- 抽出:グループを使って「欲しい部分だけ」を取り出す
- 置換:文字列の一部を「別の文字列」に変える
- メールアドレス抽出:よくある実用パターン
- 電話番号抽出:日本の電話番号をざっくり扱う
- Day 19ミニテンプレート:メール&電話抽出ツール
- Day 19のまとめ
- Day 19:正規表現で「テキストデータ抽出ツール」を作る
- テキストデータ抽出ツールの全体像をイメージする
- reモジュールの基本をツールの文脈で押さえる
- メールアドレス抽出の関数を作る
- 電話番号抽出の関数を作る
- 検索と抽出をユーザーに見せる
- 置換:機密情報をマスクする
- テキスト入力のインターフェースを作る
- テキストデータ抽出ツールの全体テンプレート
- Day 19(制作編)のまとめ
Day 19:正規表現で「文字列を賢く扱う」力を身につける
Day 19では、Pythonの標準ライブラリ re を使って、 文字列の「検索」「抽出」「置換」、そして実用的な例として「メールアドレス抽出」「電話番号抽出」を学んでいきます。 正規表現は最初は少しとっつきにくいですが、「パターンで文字列を扱う道具」として理解すると、一気に世界が広がります。
正規表現とreモジュールの基本
正規表現とは何か
正規表現(Regular Expression)は、「文字列のパターン」を表現するための記法です。 例えば、
- 数字だけの文字列
- メールアドレスっぽい文字列
- 日付のような文字列(
2026-08-30など)
を「ルール」で表現し、そのルールに合う部分を検索・抽出・置換できます。
Pythonでは、re モジュールが正規表現を扱うための標準ライブラリです。
import re # 正規表現を扱う標準ライブラリ
Python検索:文字列の中から「パターンに合う部分」を探す
re.search() の基本
re.search() は、「文字列の中から、パターンに合う最初の1箇所」を探します。
import re
text = "今日は2026年08月30日です。"
# 数字が連続する部分(1回以上)を探すパターン
pattern = r"\d+" # \d は「数字」、+ は「1回以上の繰り返し」
match = re.search(pattern, text)
if match:
print("見つかった部分:", match.group()) # group() で「マッチした文字列」を取得
else:
print("パターンに合う部分は見つかりませんでした。")
Pythonここでの重要ポイントは、
- 文字列の前に
rを付けていること(r"..."は「生文字列リテラル」で、\をそのまま書けます) \dが「数字1文字」、+が「1回以上の繰り返し」を意味することmatch.group()で「実際にマッチした文字列」を取り出せること
です。
re.findall() で「全部」見つける
re.findall() は、「文字列の中から、パターンに合う部分をすべてリストで返す」関数です。
import re
text = "ID: 123, Code: 456, Number: 789"
pattern = r"\d+" # 数字が1文字以上連続する部分
numbers = re.findall(pattern, text)
print("見つかった数字の一覧:", numbers) # ['123', '456', '789']
Python抽出:グループを使って「欲しい部分だけ」を取り出す
() で「グループ」を作る
正規表現では、() を使って「グループ」を作ることで、 マッチした全体の中から「特定の部分だけ」を取り出すことができます。
import re
text = "今日は2026年08月30日です。"
# 年・月・日をそれぞれグループとして抽出するパターン
pattern = r"(\d{4})年(\d{2})月(\d{2})日"
match = re.search(pattern, text)
if match:
year = match.group(1) # 1番目のグループ
month = match.group(2) # 2番目のグループ
day = match.group(3) # 3番目のグループ
print("年:", year)
print("月:", month)
print("日:", day)
else:
print("日付のパターンに合う部分は見つかりませんでした。")
Pythonここでの重要ポイントは、
\d{4}が「数字4桁」、\d{2}が「数字2桁」を意味すること()で囲んだ部分が「グループ」として扱われ、group(1)・group(2)…で取り出せること
です。これにより、「1つのマッチの中から、複数の要素を分解して取り出す」ことができます。
置換:文字列の一部を「別の文字列」に変える
re.sub() の基本
re.sub() は、「パターンに合う部分を、指定した文字列に置き換える」関数です。
import re
text = "この文章には秘密の単語SECRETが含まれています。SECRETは伏せます。"
# 'SECRET' を '*****' に置き換える
pattern = r"SECRET"
replaced = re.sub(pattern, "*****", text)
print("元の文章:", text)
print("置換後の文章:", replaced)
Pythonグループを使った高度な置換
グループを使うと、「マッチした一部を使って新しい文字列を作る」こともできます。
import re
text = "日付: 2026-08-30"
# 年・月・日をグループとして抽出し、表示形式を変える
pattern = r"(\d{4})-(\d{2})-(\d{2})"
# \1, \2, \3 は、それぞれ1番目〜3番目のグループを指します
replaced = re.sub(pattern, r"\1年\2月\3日", text)
print("元の文章:", text)
print("置換後の文章:", replaced)
Pythonここでのポイントは、
- 置換文字列の中で
\1・\2・\3を使うと、「グループの中身」を再利用できること - 正規表現を使うと、「フォーマット変換」が柔軟にできること
です。
メールアドレス抽出:よくある実用パターン
シンプルなメールアドレス抽出パターン
メールアドレスの正規表現は本格的にやるとかなり複雑ですが、 ここでは「よくある形式」を対象にしたシンプルなパターンで考えます。
import re
text = """
お問い合わせは info@example.com までお願いします。
サポート窓口 support@my-service.jp もご利用いただけます。
"""
# シンプルなメールアドレス抽出パターン
pattern = r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}"
emails = re.findall(pattern, text)
print("抽出されたメールアドレス一覧:")
for email in emails:
print(" -", email)
Pythonこのパターンの意味をかみ砕いて説明すると、
[A-Za-z0-9._%+-]+- 英数字・ドット・アンダースコア・パーセント・プラス・ハイフンが1文字以上
- → メールアドレスの「ローカル部」(@の前)をざっくり表現
@- 文字通りのアットマーク
[A-Za-z0-9.-]+- 英数字・ドット・ハイフンが1文字以上
- → ドメイン名の本体部分
\.[A-Za-z]{2,}- ドット+英字2文字以上(例:
.com,.jp,.infoなど)
- ドット+英字2文字以上(例:
という構造になっています。
電話番号抽出:日本の電話番号をざっくり扱う
ハイフン区切りの電話番号パターン
日本の電話番号(固定電話・携帯電話)をざっくり抽出する例です。 ここでは、「数字とハイフンで構成された電話番号」を対象にします。
import re
text = """
代表電話: 03-1234-5678 までお電話ください。
携帯: 090-1111-2222 でも受け付けています。
内線番号 1234 は対象外です。
"""
# シンプルな電話番号抽出パターン(ハイフン区切り)
pattern = r"\d{2,4}-\d{2,4}-\d{3,4}"
phones = re.findall(pattern, text)
print("抽出された電話番号一覧:")
for phone in phones:
print(" -", phone)
Pythonこのパターンの意味は、
\d{2,4}→ 数字2〜4桁-→ ハイフン\d{2,4}→ 数字2〜4桁-→ ハイフン\d{3,4}→ 数字3〜4桁
という構造で、「03-1234-5678」「090-1111-2222」などをざっくりカバーします。
Day 19ミニテンプレート:メール&電話抽出ツール
最後に、Day 19で学んだ内容をまとめた「メールアドレス&電話番号抽出ツール」のテンプレートを示します。
# day19_regex_tool.py
# 正規表現を使ったメールアドレス・電話番号抽出ツール
import re
def extract_emails(text: str):
"""テキストからメールアドレスを抽出する関数です。"""
pattern = r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}"
return re.findall(pattern, text)
def extract_phones(text: str):
"""テキストから電話番号(ハイフン区切り)を抽出する関数です。"""
pattern = r"\d{2,4}-\d{2,4}-\d{3,4}"
return re.findall(pattern, text)
def main():
print("=== Day 19:正規表現抽出ツール ===")
print("テキストを入力してください(空行で終了します)。")
lines = []
while True:
line = input()
if line == "":
break
lines.append(line)
text = "\n".join(lines)
emails = extract_emails(text)
phones = extract_phones(text)
print("\n▼ 抽出結果")
print("--------------------")
if emails:
print("メールアドレス:")
for email in emails:
print(" -", email)
else:
print("メールアドレスは見つかりませんでした。")
print("--------------------")
if phones:
print("電話番号:")
for phone in phones:
print(" -", phone)
else:
print("電話番号は見つかりませんでした。")
if __name__ == "__main__":
main()
Pythonこのツールに、メール本文やログ、問い合わせフォームの内容などを貼り付けることで、 「メールアドレスと電話番号だけを抽出する」処理を簡単に試すことができます。
Day 19のまとめ
Day 19では、正規表現と re モジュールを通して、
re.search()・re.findall()による「検索」と「抽出」()グループとgroup()による「部分的な取り出し」re.sub()による「置換」と、グループを使ったフォーマット変換- シンプルなメールアドレス抽出パターン
- 日本の電話番号をざっくり抽出するパターン
をステップバイステップで体験していただきました。
ここまで来ると、「正規表現は難しい記号の羅列ではなく、文字列のパターンを表現するための強力な道具だ」という感覚が少し育っているはずです。 この感覚は、今後の実践Python編でログ解析・テキスト処理・入力チェックなどを行ううえで、非常に頼もしい武器になっていきます。
Day 19:正規表現で「テキストデータ抽出ツール」を作る
Day 19の制作編では、標準ライブラリ re を使って、 テキストから「欲しい情報だけ」を抜き出したり、マスクしたりできる「テキストデータ抽出ツール」を作っていきます。 メールアドレスや電話番号の抽出を中心に、検索・抽出・置換の流れを、初心者向けにかみ砕いて解説します。
テキストデータ抽出ツールの全体像をイメージする
どんなことができるツールか
今回作るテキストデータ抽出ツールは、次のような機能を持つことを目標にします。
- ユーザーが入力したテキストから、正規表現でパターン検索を行う
- メールアドレスを抽出して一覧表示する
- 電話番号を抽出して一覧表示する
- 機密情報(メールアドレス・電話番号)をマスクしたテキストを生成する(置換)
この中で、
- 検索・抽出 →
re.search()・re.findall() - 置換 →
re.sub() - メールアドレス抽出 → メールアドレス用の正規表現
- 電話番号抽出 → 電話番号用の正規表現
を自然に使っていきます。
reモジュールの基本をツールの文脈で押さえる
reをインポートする
まずは、正規表現を扱うための標準ライブラリ re をインポートします。
import re # 正規表現を扱う標準ライブラリ
Python正規表現パターンは、r"..." のような「生文字列リテラル」で書くのが基本です。 これは、\d や \s などの「バックスラッシュ付きの記号」をそのまま書けるようにするためです。
メールアドレス抽出の関数を作る
シンプルなメールアドレスパターン
まずは、テキストからメールアドレスを抽出する関数を作ります。
import re
def extract_emails(text: str):
"""テキストからメールアドレスを抽出する関数です。"""
# シンプルなメールアドレス抽出パターン
pattern = r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}"
# findall() で、パターンに合う部分をすべてリストで取得します
emails = re.findall(pattern, text)
return emails
Pythonこのパターンの意味をかみ砕いて説明すると、次のようになります。
[A-Za-z0-9._%+-]+- 英字・数字・ドット・アンダースコア・パーセント・プラス・ハイフンが1文字以上
- → メールアドレスの「@の前の部分」をざっくり表現しています。
@- 文字通りのアットマークです。
[A-Za-z0-9.-]+- 英字・数字・ドット・ハイフンが1文字以上
- → ドメイン名の本体部分です。
\.[A-Za-z]{2,}- ドット+英字2文字以上(例:
.com,.jp,.infoなど)
- ドット+英字2文字以上(例:
このように、「メールアドレスっぽい文字列」をざっくり抽出することができます。
電話番号抽出の関数を作る
ハイフン区切りの電話番号パターン
次に、日本の電話番号(固定電話・携帯電話)をざっくり抽出する関数を作ります。
import re
def extract_phones(text: str):
"""テキストから電話番号(ハイフン区切り)を抽出する関数です。"""
# シンプルな電話番号抽出パターン
pattern = r"\d{2,4}-\d{2,4}-\d{3,4}"
phones = re.findall(pattern, text)
return phones
Pythonこのパターンの意味は次の通りです。
\d{2,4}→ 数字2〜4桁-→ ハイフン\d{2,4}→ 数字2〜4桁-→ ハイフン\d{3,4}→ 数字3〜4桁
これにより、「03-1234-5678」「090-1111-2222」などの形式をざっくりカバーできます。
検索と抽出をユーザーに見せる
検索結果を表示する関数
抽出したメールアドレスや電話番号を、ユーザーに分かりやすく表示する関数を作ります。
def show_extracted_data(emails, phones):
"""抽出されたメールアドレスと電話番号を表示する関数です。"""
print("\n▼ 抽出結果")
print("--------------------")
if emails:
print("メールアドレス:")
for email in emails:
print(" -", email)
else:
print("メールアドレスは見つかりませんでした。")
print("--------------------")
if phones:
print("電話番号:")
for phone in phones:
print(" -", phone)
else:
print("電話番号は見つかりませんでした。")
Pythonここでは、
- 「見つかった場合」と「見つからなかった場合」でメッセージを分けていること
- リストをそのまま表示するのではなく、1件ずつ丁寧に表示していること
がポイントです。
置換:機密情報をマスクする
メールアドレスと電話番号を「伏字」にする
テキストデータ抽出ツールの実用的な機能として、 メールアドレスや電話番号を「伏字」に置き換える処理を追加します。
import re
def mask_emails(text: str):
"""テキスト中のメールアドレスを伏字に置き換える関数です。"""
pattern = r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}"
masked_text = re.sub(pattern, "[EMAIL]", text)
return masked_text
def mask_phones(text: str):
"""テキスト中の電話番号を伏字に置き換える関数です。"""
pattern = r"\d{2,4}-\d{2,4}-\d{3,4}"
masked_text = re.sub(pattern, "[PHONE]", text)
return masked_text
Pythonここでの重要ポイントは、
re.sub(pattern, "[EMAIL]", text)のように、パターンに合う部分を一括で置き換えていること- 「伏字」の表現を
[EMAIL]や[PHONE]としておくことで、後から機械的に処理しやすいこと
です。ログや問い合わせ内容を共有するときに、「個人情報だけ伏せる」といった用途に向いています。
メールと電話をまとめてマスクする
メールアドレスと電話番号の両方をマスクしたテキストを生成する関数を作ります。
def mask_sensitive_data(text: str):
"""テキスト中のメールアドレスと電話番号をまとめて伏字にする関数です。"""
text = mask_emails(text)
text = mask_phones(text)
return text
Pythonテキスト入力のインターフェースを作る
複数行テキストを受け取る
ユーザーに複数行のテキストを入力してもらい、それを1つの文字列として扱う関数を作ります。
def read_multiline_text():
"""複数行のテキストを入力してもらい、1つの文字列として返す関数です。"""
print("テキストを入力してください(空行で終了します)。")
lines = []
while True:
line = input()
if line == "":
break
lines.append(line)
text = "\n".join(lines)
return text
Pythonこの形にしておくと、メール本文やログ、問い合わせ内容などをそのまま貼り付けて使うことができます。
テキストデータ抽出ツールの全体テンプレート
ここまでの関数を組み合わせて、「テキストデータ抽出ツール」として動く全体コードをまとめます。
# day19_text_extract_tool.py
# 正規表現を使ったテキストデータ抽出ツール
import re
def extract_emails(text: str):
"""テキストからメールアドレスを抽出する関数です。"""
pattern = r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}"
return re.findall(pattern, text)
def extract_phones(text: str):
"""テキストから電話番号(ハイフン区切り)を抽出する関数です。"""
pattern = r"\d{2,4}-\d{2,4}-\d{3,4}"
return re.findall(pattern, text)
def mask_emails(text: str):
"""テキスト中のメールアドレスを伏字に置き換える関数です。"""
pattern = r"[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Za-z]{2,}"
return re.sub(pattern, "[EMAIL]", text)
def mask_phones(text: str):
"""テキスト中の電話番号を伏字に置き換える関数です。"""
pattern = r"\d{2,4}-\d{2,4}-\d{3,4}"
return re.sub(pattern, "[PHONE]", text)
def mask_sensitive_data(text: str):
"""テキスト中のメールアドレスと電話番号をまとめて伏字にする関数です。"""
text = mask_emails(text)
text = mask_phones(text)
return text
def read_multiline_text():
"""複数行のテキストを入力してもらい、1つの文字列として返す関数です。"""
print("テキストを入力してください(空行で終了します)。")
lines = []
while True:
line = input()
if line == "":
break
lines.append(line)
text = "\n".join(lines)
return text
def show_extracted_data(emails, phones):
"""抽出されたメールアドレスと電話番号を表示する関数です。"""
print("\n▼ 抽出結果")
print("--------------------")
if emails:
print("メールアドレス:")
for email in emails:
print(" -", email)
else:
print("メールアドレスは見つかりませんでした。")
print("--------------------")
if phones:
print("電話番号:")
for phone in phones:
print(" -", phone)
else:
print("電話番号は見つかりませんでした。")
def main():
print("=== Day 19:テキストデータ抽出ツール ===")
text = read_multiline_text()
while True:
print("\nメニュー:")
print("1: メールアドレスと電話番号を抽出して表示する")
print("2: メールアドレスと電話番号を伏字にしたテキストを表示する")
print("3: 終了する")
choice = input("番号を入力してください: ").strip()
if choice == "1":
emails = extract_emails(text)
phones = extract_phones(text)
show_extracted_data(emails, phones)
elif choice == "2":
masked = mask_sensitive_data(text)
print("\n▼ 伏字にしたテキスト")
print("--------------------")
print(masked)
elif choice == "3":
print("テキストデータ抽出ツールを終了します。")
break
else:
print("1〜3の番号を入力してください。")
if __name__ == "__main__":
main()
PythonDay 19(制作編)のまとめ
Day 19の制作編では、「テキストデータ抽出ツール」を通して、
re.findall()によるメールアドレス・電話番号の抽出- 正規表現パターンの意味を、記号レベルでかみ砕いて理解すること
re.sub()による機密情報のマスク(伏字化)- 複数行テキストを扱うインターフェースの作り方
を一つのプログラムの中で体験していただきました。
ここまで来ると、「正規表現を使って、テキストから欲しい情報だけを抜き出したり、守りたい情報だけを伏せたりできる」という感覚が少し育っているはずです。 この感覚は、今後の実践Python編でログ解析・入力チェック・データ前処理などを行ううえで、非常に頼もしい武器になっていきます。
