2016-08-01 2 views
3
var url = 'https://mp.weixin.qq.com/s?__biz=MzAxNjczMTQxMA==&mid=504131096&idx=1&sn=c2fe41152807821b7916fa9539a0cf87&scene=1&srcid=0718JR98ETFngTl6mDsNRfhK&key=77421cf58af4a65374324bd2f16d7fdd913230b5ab4bd48a72759cc99919893795265ff20c0c8a79c676e636f789899c&ascene=0&uin=MjAzOTExMTUxMg%3D%3D&devicetype=iMac15%2C1+OSX+OSX+10.11.5+build(15F34)&version=11020201&pass_ticket=kA76WNrCKCEZ3JyEii3tYs88BCmLEM%2FI4LPD%2FtHBzoPjYzI9t7seUadtUUVQ9677'; 
var reg = /^(http(s)?:\/\/)?(([\w\.]+)\.(?:com|cn|love|net|com\.cn|org)(\/|#|!|%|\w|\d|&|\?|-|=|~|\.|\+)*)$/; 
url.match(reg); 

URLを検証するかどうかをテストしたいが、matchステートメントはプロセスをCRASHに導く! - ブラウザやiOSアプリケーションは、後で応答しません、CPUは90%+常に、無限ループ内にありますか? 私のregが間違っているのですか、これは正規表現のバグですか?これは正規表現のバグですか?

私はJavaScript(http://regexr.com/)、ノード、およびiOSでテストしましたが、タイムアウトか応答なし(クラッシュ)です。

+2

1つのことは確実です。問題は壊滅的なバックトラッキングです。 '(\ | | | | |%| \ w | \ d |&| \?| - | = |〜| \。| \ +)*'グループがそれを殺して、 \ /#!%\ w&?\ - =〜。+] * '。 –

+0

http://www.regular-expressions.info/catastrophic.html – daveoncode

答えて

4

問題は最後の交代グループは、文字列(すなわち\w\d)内の同じ場所に一致するいくつかの支店を持っているということで、そのグループに設定された*数量詞が前にすべての可能な組み合わせを試してハードワークをバックトラックになりマッチは失敗する。私は正規表現を台無しにしないようにパターンがしようとしている場合-は、文字クラス内のエスケープ保持regex demo

注を参照してください

/^(http(s)?:\/\/)?(([\w.]+)\.(?:com|cn|love|net|com\.cn|org)[\/#!%\w&?\-=~.+]*)$/ 

:あなたは[\/#!%\w&?\-=~.+]文字クラスを使用する必要が

将来更新される可能性があります(-は、正規表現の末尾または先頭にリテラルハイフンを表すことができますが、文字クラスの最後にシンボルを追加する傾向があり、時には-という範囲を知らずに範囲を作成する傾向があります)それ)。

+1

より正確に言うと、最も簡単な修正は、最後のグループから '\ d'を削除するだけで、[すでに動作しています](https: //regex101.com/r/lC1hA5/1)、文字クラスの解決策は(はるかに効率的です)(https://regex101.com/r/jT8pR3/1)(691ステップ対4590ステップ)です。 –

+0

恐ろしい!あなたの答えは非常に明確で正しい。私は同時に(\ w | \ d)を置くことができないのかどうかはわかりませんでしたが、それはほとんどのテスト文字列の値でも機能します(私はこのエラーを早く見つけられませんでした)。そして、はい、それをキャプチャして、http://またはhttps://または空であるかどうかを判断したいと思います。どうもありがとう! –

+0

もう一度正確に言えば、あなたは '\ w | \ d'を使うことができますが、より大きなパターンの中でそれを使用し、量子を交替グループに設定すると、悲惨なバックトラックが遅くなります。 **交替を使用する場合、同じ場所で一致するブランチがないことを確認することがベストプラクティスです**。だから、 '' catastrophical(catastrophic) ''を使ってはいけません。あなたがそれを得ることを望みます:) –

関連する問題