正規表現 例題。。。
生成AIに
丸投げ! 依頼の 日々!
正規表現
パターンを
いちいち 丸投げ するのも
面倒である
で
ちょっと 挑戦してみた!
# ★ パターンと保存先をセットで書く
RULES = [
# AFTR00AJ
(r'^[A-Z]{4}[0-9]{2}[A-Z]{2}', "A-Z系"),
# GLOS0001
(r'^[A-Z]{4}[0-9]{4}', "D-Z系"),
# RANDA008
(r'^[A-Z]{5}[0-9]{3}', "E-Z系"),
# TIME02P1
(r'^[A-Z]{4}[0-9]{2}[A-Z][0-9]', "F-Z系"),
# THECODNT
(r'^[A-Z]{8}', "G-Z系"),
# AlbumArt
(r'^(AlbumArt).*', "AlbumArt"),
]
こんな 感じで どうでしょうか???
【Gemini】様に 採点をお願いした
ご提示いただいたコード、非常に整理されていて素晴らしいですね!
実務でよく使われる「リストにタプルを格納してループで回す」という、拡張性
の高いスマートな書き方です。
初歩的な正規表現の使い方として、現在のパターンが意図通りに動くか、また「
ここを意識するとさらに堅牢になる」というポイントをまとめました。
1. 各パターンの解説とセルフチェック
提示された正規表現を整理すると、以下のようになります。
| パターン | 意味 | 例 |
| `^[A-Z]{4}[0-9]{2}[A-Z]{2}` | 英4 + 数2 + 英2 | `AFTR00AJ` |
| `^[A-Z]{4}[0-9]{4}` | 英4 + 数4 | `GLOS0001` |
| `^[A-Z]{5}[0-9]{3}` | 英5 + 数3 | `RANDA008` |
| `^[A-Z]{4}[0-9]{2}[A-Z][0-9]` | 英4 + 数2 + 英1 + 数1 | `TIME02P1` |
| `^[A-Z]{8}` | 英8文字 | `THECODNT` |
| `^(AlbumArt).*` | 先頭がAlbumArtで始まる | `AlbumArt_01` |
2. さらに良くするためのアドバイス
# ① 「末尾」を意識する(重要)
現在の書き方だと、例えば `^[A-Z]{8}`(G-Z系)は、「英字が8文字以上」ある
場合、後ろに何が続いていてもマッチしてしまいます。
> 例:`THECODNT_EXTRA_DATA` も `G-Z系` に判定される。
もし「8文字ぴったり」のものだけを抽出したい場合は、
末尾を表す `$` をつけるのが定石です。
* 修正例:`(r'^[A-Z]{8}$', "G-Z系")`
# ② 判定の優先順位
`RULES` を上から順番に判定していく場合、「条件が厳しいもの(具体的なもの
)」を上に、「条件が緩いもの(抽象的なもの)」を下に書くのがコツです。
現状のリストは文字数や構成がはっきり分かれているので問題なさそうですが、
今後ルールが増えたときに意識してみてください。
# ③ `AlbumArt` のキャプチャ
`(AlbumArt).*` のカッコ `()` は「グループ化」を意味します。もし `AlbumAr
t` という文字列そのものを後で取り出す必要がなければ、
カッコを外して `^AlbumArt.*` としてもOKです。
実装イメージ(Python)
この `RULES` を使って判定する際の標準的なコード例です。
```python
import re
def classify_code(text):
for pattern, label in RULES:
# re.match は先頭からの一致を確認します
if re.match(pattern, text):
return label
return "不明"
# テスト
print(classify_code("AFTR00AJ")) # 出力: A-Z系
print(classify_code("AlbumArt_v1")) # 出力: AlbumArt
```
まとめ
「初歩」というには十分すぎるほど、実戦的で読みやすい構成です!
特に `r'...'`(raw文字列)をしっかり使っている点は、正規表現のバックスラ
ッシュ地獄を避けるための必須テクニックなので、バッチリですね。
このまま進めて問題ないと思いますが、「文字数がぴったりの時だけマッチさせ
たいか?」だけ、用途に合わせて `$` を足すか検討してみてください。
# ==============================
おっしゃる通り、正規表現の記号は似ているので混同しやすいですよね。
今回の `()`(カッコ) の役割について、少しだけ掘り下げて整理してみましょ
う。ここを理解すると、正規表現がもっと自由自在に扱えるようになります!
1. 記号の役割まとめ
| 記号 | 呼び方 | 役割 | イメージ |
| `[]` | 文字クラス | 「どれか1文字」の候補 | `[ABC]` → AかBかCのどれか
1文字 |
| `{}` | 量指定子 | 「繰り返す回数」 | `A{3}` → AAA |
| `()` | グループ化 | 「ひとまとめ」 + 「保存」 | `(ABC)` → 「ABC」と
いう塊として扱う |
2. なぜ `(AlbumArt)` のカッコがなくてもいいのか?
正規表現は、何も囲わなくても書いた順番通りに並んでいる文字列を探しに行き
ます。
* `AlbumArt` と書くだけで、「A」の次に「l」、その次に「b」…という並び
を探します。
* そのため、単純に「その文字があるか」を判定するだけなら `()` は不要な
んです。
# では、いつ `()` を使うのか?
主に以下の2つのケースで使います。
1. 一部だけを抜き出したいとき(キャプチャ)
「ファイル名全体にマッチさせつつ、中の数字の部分だけ後で取り出して変
数に入れたい!」という時に `()` で囲みます。
2. 繰り返しの単位を指定したいとき
`ABC{3}` と書くと、最後の「C」だけが3回繰り返されます(ABCCC)。
`(ABC){3}` と書くと、「ABC」が3回繰り返されます(ABCABCABC)。
3. `^AlbumArt.*` の意味
今回のファイル名の例で見てみましょう。
> AlbumArt-A02468.wav
これを `^AlbumArt.*` で表すと:
* `^` : 行の先頭からスタートして
* `AlbumArt` : 「AlbumArt」という文字が並んでいて
* `.` : その後に「何らかの文字」が
* `*` : 0文字以上続いている(つまり、残り全部)
という意味になります。
「先頭が `AlbumArt` で始まってさえいれば、後ろは何でもいいよ!」というル
ールになるので、ご提示のファイル名には完璧にマッチします。
豆知識:より厳密にするなら
もし「ハイフン以降もしっかりチェックしたい」となったら、こんな書き方もで
きます。
`(r'^AlbumArt-[A-Z][0-9]{5}\.wav$', "AlbumArt系")`
* `[A-Z]` : アルファベット1文字
* `[0-9]{5}` : 数字5桁
* `\.wav` : 最後に `.wav` で終わる(`.` は特殊な意味を持つので `\` で
打ち消します)
今の `^AlbumArt.*` は「とりあえずAlbumArtで始まるものを全部キャッチする
」という、網羅性の高い良いルールだと思います!
何か特定の「この部分だけ取り出したい!」という要望が出てきたら、その時こ
そ `()` の出番ですので、ぜひ試してみてくださいね。
# ==============================
本日の まとめ
$ を 付与した方が いいよ!
文字列 だけの 単純なら
()で 囲まなくても 動作する
勉強する
お年頃♪
じじぃ~
