正規表現でhtmlからのタグ抽出

2007/08/09 | PHPで正規表現

<div>ab</div><div>cd</div><div>ef</div>

こういう文字列があるとする。ここから正規表現でab、cd、efという文字列を抽出したいのだが、正規表現の記述で悩んだのでメモ。

(1) 最初はこのような正規表現を書いてみた。
!<div>(.*)</div>!

しかしこれだとなぜか一番最初の<div>と一番最後の</div>にマッチしてしまう。なぜ?。

(2) そこで数時間調べに調べてこんな正規表現に行き着いた。
!<div>(.*?)</div>!

見てのとおり「?」が一つついただけ。しかしたったそれだけで期待する結果を配列で得ることが出来た。「.」は任意の1文字で「*」は0回以上の繰り返し、「?」は0回または1回で「()」はパターンを表す・・・。で結局「(.*)」と「(.*?)」とでは何が違うのか・・・全然わからない。

まだまだ修行が足りないということなのだが、両者の違いを明確に教えていただける人がいれば、是非解説をお願いします。

4件のコメント

  1. tomo :

    この場合は、[「?」は0回または1回]ではなく、違う意味で使う[?]ですよ。
    うまく文にして説明はできないので
    http://jp2.php.net/manual/ja/reference.pcre.pattern.syntax.php
    このページの[繰り返し]の項目の[表 245. 単一文字の量指定子]の下あたりからの説明を読んでみてください。

  2. かおるん :

    コメントありがとです。
    読んでみました。「わかりましたか?」と質問されると「わかりません」としか答えられないのですが、なんとなくニュアンスをつかめたような気がします。
    やっぱりオライリー読まないとだめですかね・・・。

  3. :

    *? や +? は組み合わせて意味を持つものです。

    * や + は最長一致で
    *? や +? は最短一致ですね。

    最長一致とは、名前の通りその正規表現で一致する文字列のうち最も長いもの、
    最長一致とは、その正規表現で一致する文字列のうち最も短いものを表します。

  4. かおるん :

    この投稿を見つけていただき、しかも名回答ありがとうございます。
    大変勉強になりました。

コメントを残す


守谷市(まちの情報ポータル) 無料アンケートレンタルjpForm.net