目次
- 目次
- 正規表現とは?
- 正規表現の表現方法
- よく使う正規表現の組み合わせ
- Pythonの正規表現ライブラリreの使い方
- Jetbrains IDEで正規表現のテストをする
- 参考資料
- MyEnigma Supporters
正規表現とは?
正規表現は文字列の集合を表す表現方法で、
文字列におけるパターンマッチングによく使用される方法です。
いわゆる、あいまい検索を実施したい時によく使用します。
プログラマの人にとっては、
ある関数がその他のソースコードの
どこで使用されているかを調べる時に
grepを使う人も多いと思いますが、
このgrepで検索する時に正規表現を使うことができます。
それ以外にも、
テキストデータをプログラミング言語を使って
検索して制御するような
しかし、この正規表現はかなり取っ付きづらい表現方法なので、
わかりやすいようにまとめておきたいと思います。
正規表現の表現方法
正規表現の例について説明します。
ひとつ注意点として、
一般的な正規表現は殆どのツールやライブラリでも
共通で使用できると思いますが、
それぞれのツールにおいて、
独特な記法が追加されていることもありますので
注意が必要です。
下記の説明の(python)は
pythonの正規表現ライブラリreの特有の表現です。
詳しくはこちら
行頭
^
行頭がDataという行は、下記のように表現されます。
^Data
冒頭に#があり、それ以降が何でも良い場合は、
^#.*
になります。
行末
$
行末がEndという行は、下記のように表現されます。
End$
任意の一文字
. (ピリオド)
指定の一文字
abcのどれかに一致する場合は、下記です。
[abc]
ひとつ前の文字か正規表現が0個以上繰り返される
*
例えば、.*bc とすると、なにか文字0個以上あり、
そのあと、bcという文字が続くような文字列がマッチします。
ちなみに、0個以上繰り返すので、繰り返さなくても良いことを考えると、
なんでも有りな文字列になりますので注意してください。
下記のようにすると、aが含まれなくても抽出されてしまいます。
a*
ひとつ前の文字か正規表現が1個以上繰り返される
例えば、a または aa または、aaaなど、
aが一つ以上繰り返す文字列は下記で表現されます。
a+
ひとつ前の文字か正規表現が0個または1個繰り返される
?
繰り返しの回数が制限されていることに注意が必要です。
例えば、
.?bc
は、何でも良いがなにか文字が0個か、1個あり、その後、bcが続く文字列がマッチします。
また、最短マッチを指定するときにも、最後に?を置くことで利用されます。例) <.*?>
任意の数字
[0-9] or \d (python)
任意の非数字
[^0-9] or \D (python)
任意の空白文字
[\t\n\r\f\v] or \s (python)
任意の非空白文字
[^\t\n\r\f\v] or \S (python)
任意の英数文字および下線
[a-zA-Z0-9_] or \w (python)
任意の非英数文字と非下線
[^a-zA-Z0-9_] or \W (python)
エスケープシーケンス
特殊文字は下記のようなエスケープシーケンスとの
組み合わせで表現できます。
特殊文字 | 説明 |
---|---|
\t | タブ |
\n | 改行 |
\z | End of file |
\r | キャリッジリターン |
グルーピング
一つの文字ではなく、文字列の繰り返しを表現したい場合は、
丸括弧 ()を使います。
例えば、"わい"という言葉が繰り返される場合は、
(わい)+
という正規表現で表現できます。
よく使う正規表現の組み合わせ
一般的に、上記の正規表現を複数組み合わせて
文字列を表現することが多いですが、
よく使用する正規表現の組み合わせをまとめておきます。
空行を表す
^$
ある単語のみを含んだ行を表す
lineという単語のみを含んだ行の場合、
^line$
任意の長さの文字列
.*
これは非常によく使用します。
たとえば、あるCコードのforループの先頭行を取得したい場合は、
下記の正規表現を使うことができます。
for(.*){
指定の桁の数
例えば、3桁の数字をマッチしたい場合は、
[0-9]{3}
のように表現できます。
Pythonの正規表現ライブラリreの使い方
Pyhtonには便利な正規表現ライブラリreが、
デフォルトでインストールされています。
本章ではreの使い方の概要を説明します。
正規表現の事前コンパイル
大抵のreライブラリの関数は、
正規表現と検索対象の文字列を入れれば、処理をしてくれますが、
同じような正規表現を何度も使う場合は、
事前に正規表現をコンパイルしておくようにすると、
計算速度が向上します。
例えば、
ある文字列strに"abc"が含まれているか
どうかをチェックしたい場合は、
match(".*abc.*", str)
とすればboolで結果が返ってきますが、
この正規表現を頻繁に使う場合は、
下記のように事前コンパイルしておくと
速度が早くなります。
p = re.compile(r'.*abc.*')
p.match(str)
正規表現による文字列検索
matchとsearchという関数を使います。
事前コンパイルをしている場合は、下記のような関数引数を与えます。
match(string [,pos = 0] [,endpos])
search(string [,pos = 0] [,endpos])
posとendposは検索を開始する文字列の位置です。
省略すると文字列全体検索になります。
matchとsearchの違いですが、
search() は文字列の中から正規表現と一致する部分文字列を検索しますが、
match() は文字列の先頭から正規表現とマッチングするか調べるだけです。
ですので、正規表現を正確に表現しないとmatchではマッチングしません。
正規表現による文字列置換
subという関数を使います。
sub(hoge, huga, str [,count])
sub(huga, str [,count]) #事前コンパイル済みの場合
上記ように指定すると、str文字列の中のhogeをhugaに変換することができます。
countは文字列置換を実施する回数で、デフォルトは0で回数制限無しです。
置換の回数を制限したい場合は、このcountを指定しましょう。
文字列置換例
p = re.compile('abc')
p.sub('aaa', 'abc def abc ghi') # 置換結果 'aaa def aaa ghi'
p.sub('123', 'abc def abc ghi', 1) # 置換結果'aaa def abc ghi'
より詳細な使い方
こちらを参照下さい
Jetbrains IDEで正規表現のテストをする
PythonのIDEであるPycharmや、JavaのIDEであるIntelijである
Jetbrains社のIDEでは、簡単に自分が作成した正規表現を、
テストすることができます。
おお、Pycharm(Intelij)、自分が書いた正規表現のテストが簡単にできるのか。。。すごい。:Regular expression syntax reference—IntelliJ IDEA https://t.co/f4DOv69Ifb pic.twitter.com/uq4EPgI0Je
— Atsushi Sakai (@Atsushi_twi) 2020年12月22日
参考資料
MyEnigma Supporters
もしこの記事が参考になり、
ブログをサポートしたいと思われた方は、
こちらからよろしくお願いします。