1

現時点では制御できないアプリケーションを使用してこの Web サイトを検索していますが、正規表現のみを使用して重複一致を無視する方法があるかどうか疑問に思っていました。

今、ページのソースコードの画像ソースに一致するものを取得するためにこれを書きました

これを使用してsrcを取得します

<span> <img id="imgProduct.*? src="/(.*?)" alt="

これから

<span> <img id="imgProduct_1" class="SmPrdImg selected"     
onclick="(some javascript);" src="the_src_I_want1.jpg" alt="woohee"> </span>
<span> <img id="imgProduct_2" class="SmPrdImg selected"     
onclick="(some javascript);" src="the_src_I_want2.jpg" alt="woohee"> </span>
<span> <img id="imgProduct_3" class="SmPrdImg selected"     
onclick="(some javascript);" src="the_src_I_want3.jpg" alt="woohee"> </span>

唯一の問題は、上記とまったく同じコードがソースのかなり下の方に複製されていることです。正規表現のみを使用して重複を無視または削除する方法はありますか?

4

2 に答える 2

2

あなたのパターンはあまり良くありません。現在存在しているため、正確なソースコードに固有すぎます。@Truthがコメントしたように、それが変わると、パターンが壊れます。次のようなものをお勧めします。

<img[^>]*src=['"]([^'"]*)['"]

これは、ソース コードがどれだけ変更されても、任意のタグsrc内の任意の属性の内容と一致します。<img>

正規表現との重複を防ぐには、先読みが必要です。これは非常に遅くなる可能性があります。これに正規表現を使用することはお勧めしません。これは、必要に応じてできることを示すためのものです。必要なパターンは次のようなものです (私は Notepad++ の正規表現検索を使用してこれをテストしました。これは PCRE に基づいており、JavaScript よりも堅牢ですが、JavaScript の正規表現パーサーがこれを処理できると確信しています)。

<img[^>]*src=['"]([^'"]*)['"](?!(?:.|\s)*<img[^>]*src=['"]\1['"])

次に、すべての最後のインスタンスに一致しますsrc

内訳

説明のために、パターンがどのように機能するかを次に示します。

<img[^>]*src=['"]([^'"]*)['"]

これにより、タグが表示された<img>ときにタグの内側にいることが確認srcされ、引用符の内側にあるもののみが一致することが確認されます (一重引用符または二重引用符のいずれかです。ファイル名にはどちらも有効な文字でないため、引用符の種類やエスケープされた引用符の混在について心配する必要はありません)。

(?!
    (?:
        .
    |
        \s
    )*
    <img[^>]*src=['"]\1['"]
)

(?!否定的な先読みを開始します。この時点以降、次のパターンが一致しないことを要求しています。

次に(?:.|\s)*、任意の文字または空白に一致します。これは、JavaScript.が改行に一致しないため\sです。ほとんどの場合、私は怠け者で、可能な行末のパターンを書きたくなかったので、\s. *もちろん、 は、これらをいくつでも持つことができることを意味します。これは、次の (まだ否定先読みの一部である)ファイルの残りの部分が見つからないことを意味します。(?:代わりに(、この括弧が後方参照のために記憶されないことを意味します。

そのビットは<img[^>]*src=['"]\1['"]. これは最初のパターンと非常に似ていますが、 with をキャプチャする代わりに、以前にキャプチャしたsrcwith([^'"]*)を参照していsrcます\1

したがって、パターンは「ファイルの残りのどこにも同じものがないものsrcに一致する」と言っています。つまり、それぞれの最後のインスタンスのみを取得し、重複はありません。imgimgsrcsrc

ちなみに、複数回出現する anyのすべてのインスタンスを削除したい場合は、運が悪いと思います。JavaScript は後読みをサポートしていません。また、後読みをサポートしている正規表現エンジンの圧倒的多数は、このような複雑な後読みを許可していませimgsrc

于 2012-08-20T21:07:28.773 に答える
1

私はそれらを一意にするために一生懸命働くつもりはありません.pregの後にPHPでそれを行うだけです。

$pattern = '~<span> <img id="imgProduct.*? src="/(.*?)" alt="~is';
$match   = preg_match_all($pattern, $html, $matches);

if ($match)
{
     $matches = array_unique($matches[1]);
}

JavaScript を使用している場合は、array_unique の代わりに別の関数を使用する必要があります。PHPJS を確認してください: http://phpjs.org/functions/array_unique:346

于 2012-08-20T21:25:01.727 に答える