2011-02-07 27 views
7

私は正規表現の体操をしています。私は、妥当な量のスペース内にヌルチェックが続かないオペレータとしての使用法がある場合、C#コードを検索しようとしています。今私はC#コードを解析したくありません。例えば。私はこのように任意のランダムなヌル・チェック「は良いチェックとしてカウントされますように正規表現否定先読み

var x1 = x as SimpleRes; 
    var y1 = y as SimpleRes; 
    if(x1.a == y1.a) 

としてコードスニペットをキャプチャしたいしかし、

var x1 = x as SimpleRes; 
    var y1 = y as SimpleRes; 
    if(x1 == null) 

もそのことについては

var x1 = x as SimpleRes; 
    var y1 = y as SimpleRes; 
    if(somethingunrelated == null) {...} 
    if(x1.a == y1.a) 

をキャプチャしません"したがって見つかりませんでした。

質問はです。その周辺に何か他のものが見つからないようにするにはどうすればよいですか。

私は初心者の方に「as」を探してから、150文字以内に否定的な先読みをしました。

\bas\b.{1,150}(?!\b==\s*null\b) 

上記の正規表現は、幸運にも上記の例すべてに一致します。私の勇気は私に教えてくれます。問題は先読みしてからネガティブ先読みをすると、先読みが '== null'を見つけられない多くの状況を見つけることができるということです。

私は表現全体を否定しようとすると、どちらも役に立ちません。そうすれば、ほとんどのC#コードと一致します。

+2

適切なC#パーサーを使用できませんか? – Gumbo

+2

私は最初に「私は正規表現の体操をしています。私は自分自身にC#を検索しようとしています...」 –

+0

これはフットボールを見て「体操をしているのと同じですか? :-) – xanatos

答えて

11

I 正規表現体操 !ここでコメントしたPHPの正規表現です:

$re = '/# Find all AS, (but not preceding a XX == null). 
    \bas\b    # Match "as" 
    (?=     # But only if... 
     (?:    # there exist from 1-150 
     [\S\s]   # chars, each of which 
     (?!==\s*null) # are NOT preceding "=NULL" 
    ){1,150}?   # (and do this lazily) 
     (?:    # We are done when either 
     (?=    # we have reached 
      ==\s*(?!null) # a non NULL conditional 
     )    # 
     | $    # or the end of string. 
    ) 
    )/ix' 

そして、ここではJavascriptのスタイルである:

re = /\bas\b(?=(?:[\S\s](?!==\s*null)){1,150}?(?:(?===\s*(?!null))|$))/ig; 

この1つは私の頭は、ここで少し...

を傷つける作りました私が使用しているテストデータです:

text = r""" var x1 = x as SimpleRes; 
    var y1 = y as SimpleRes; 
    if(x1.a == y1.a) 

however, not capture 
    var x1 = x as SimpleRes; 
    var y1 = y as SimpleRes; 
    if(x1 == null) 

nor for that matter 
    var x1 = x as SimpleRes; 
    var y1 = y as SimpleRes; 
    if(somethingunrelated == null) {...} 
    if(x1.a == y1.a)""" 
+0

そして、あなたがそれが否定的な条件付きテストで動作することを望むならば、例えば。 'X!= null'、単純にそれぞれを変更してください。' == 'to:' [!=] = ' – ridgerunner

+0

とてもうまくやっていて、説明が良いです。 +1。私はC#の解析に100%信頼できないという正規表現についての通常の警告を含めることにします。 –

2

は先読み内.{1,150}を入れて、(一般的には、.は改行と一致していません)\s\S.を交換してください。また\b==の近くで誤解を招く可能性があります。

\bas\b(?![\s\S]{1,150}==\s*null\b) 
+0

私はあなたのアイデアを得ることができません、それはまだ私の検索結果に上記の2番目の例が含まれています。 –

+0

この正規表現: '\ bas \ b(?![\ s \ S] {1,150} == \ s * null \ b)'はかなり近いですが、最初のセットの2番目のASと一致しません" テストデータ。 – ridgerunner

+0

@ridgerunnerはPythonでうまく動作しますか?テストするためのC#セットアップはありません。 – robert

2

私は、変数名を()に入れて、後方参照として使うことができると思います。次のようなもの

\b(\w+)\b\W*=\W*\w*\W*\bas\b[\s\S]{1,150}(?!\b\1\b\W*==\W*\bnull\b) 
2

質問は不明です。正確に何をしたいですか?私は後悔しますが、質問とコメントを何度も読んだ後も、私はまだ理解しません。

コードはC#でなければなりませんか? Pythonで?その他?この点に関する兆候はありません

if(... == ...)行がvar ... = ...行のブロックに続く場合にのみマッチングしますか?

ブロックの間に異種のラインがあり、マッチングを停止することなくラインがある可能性がありますか?

私のコードでは、2番目のオプションがtrueになります。

if(... == null)行後にif(... == ...)行が一致を停止しているかどうかを確認しますか?

「はい」か「いいえ」かを理解できないため、2つの正規表現を定義してこれらの2つのオプションをキャッチしました。

私のコードが十分明確で、あなたの先入観に答えることを願っています。

それはPythonである

import re 

ch1 ='''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(x1.a == y1.a) 
1618987987849891 
''' 

ch2 ='''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
uydtdrdutdutrr 
if(x1.a == y1.a) 
3213546878''' 

ch3='''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(x1 == null) 
165478964654456454''' 

ch4='''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
hgyrtdduihudgug 
if(x1 == null) 
165489746+54646544''' 

ch5='''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(somethingunrelated == null) {...} 
if(x1.a == y1.a) 
1354687897''' 

ch6='''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
ifughobviudyhogiuvyhoiuhoiv 
if(somethingunrelated == null) {...} 
if(x1.a == y1.a) 
2468748874897498749874897''' 

ch7 = '''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(x1.a == y1.a) 
iufxresguygo 
liygcygfuihoiuguyg 
if(somethingunrelated == null) {...} 
oufxsyrtuy 
''' 

ch8 = '''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
tfsezfuytfyfy 
if(x1.a == y1.a) 
iufxresguygo 
liygcygfuihoiuguyg 
if(somethingunrelated == null) {...} 
oufxsyrtuy 
''' 

ch9 = '''kutgdfxfovuyfuuff 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
tfsezfuytfyfy 
if(x1.a == y1.a) 
if(somethingunrelated == null) {...} 
oufxsyrtuy 
''' 

pat1 = re.compile(('(' 
        '(^var +\S+ *= *\S+ +as .+[\r\n]+)+?' 
        '([\s\S](?!==\s*null\\b))*?' 
        '^if *\(*[^\s=]+ *==(?!\s*null).+$' 
        ')' 
        ), 
        re.MULTILINE) 

pat2 = re.compile(('(' 
        '(^var +\S+ *= *\S+ +as .+[\r\n]+)+?' 
        '([\s\S](?!==\s*null\\b))*?' 
        '^if *\(*[^\s=]+ *==(?!\s*null).+$' 
        ')' 
        '(?![\s\S]{0,150}==)' 
        ), 
        re.MULTILINE) 


for ch in (ch1,ch2,ch3,ch4,ch5,ch6,ch7,ch8,ch9): 
    print pat1.search(ch).group() if pat1.search(ch) else pat1.search(ch) 
    print 
    print pat2.search(ch).group() if pat2.search(ch) else pat2.search(ch) 
    print '-----------------------------------------' 

結果

>>> 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(x1.a == y1.a) 

var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(x1.a == y1.a) 
----------------------------------------- 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
uydtdrdutdutrr 
if(x1.a == y1.a) 

var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
uydtdrdutdutrr 
if(x1.a == y1.a) 
----------------------------------------- 
None 

None 
----------------------------------------- 
None 

None 
----------------------------------------- 
None 

None 
----------------------------------------- 
None 

None 
----------------------------------------- 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
if(x1.a == y1.a) 

None 
----------------------------------------- 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
tfsezfuytfyfy 
if(x1.a == y1.a) 

None 
----------------------------------------- 
var x1 = x as SimpleRes; 
var y1 = y as SimpleRes; 
tfsezfuytfyfy 
if(x1.a == y1.a) 

None 
----------------------------------------- 
>>> 
+0

+1私は質問がかなり曖昧であることに同意します。ほとんどの人々は良い正規表現の質問は非常に正確に綴る必要があることを理解していません。 – ridgerunner

2

私はあなたの問題を再定義してみましょう:割り当て "と" 用

  1. ルック - あなたはおそらく必要が実際の代入を探すためのより良い正規表現と、代入された式を格納したいかもしれないが、今のところ "\ bas \ b"を使ってみよう。
  2. あなたがif (... == null) 150内の文字が表示された場合は、if (... == null) 150内の文字が表示されない場合は、
  3. と一致していない、試合

あなたの表現\bas\b.{1,150}(?!\b==\s*null\b)があるため、負のルックで動作しません。先に。正規表現は、このネガティブな先読みを回避するために、常に1文字の前後にスキップすることができ、if (... == null)がある場合でもマッチングが終了します。

正規表現は実際にはではありません。と一致しています。その後、

\bas\b.{1,150}\b==\s*null\b 

とチェック否定:if (!regex.match(text)) ...

1
(?s:\s+as\s+(?!.{0,150}==\s*null\b)) 
をこのケースでは、150文字以内でご確認ください「== nullがあれば」との割り当て「として」一致しようとしているの方がよいでしょう

?s:でSingleLineオプションを有効にしています。必要に応じてRegexのオプションに入れることができます。私はasの周りに "正当な"スペースしかないと思うので、\sasの周りに置いていると付け加えます。おそらく\b

(?s:\b+as\b(?!.{0,150}==\s*null\b)) 

などが \sはおそらく「有効スペース」ではありませんスペースをキャッチすることに注意して置くことができます。 [\f\n\r\t\v\x85\p{Z}]と定義され、ここで \p{Z}Unicode Characters in the 'Separator, Space' CategoryUnicode Characters in the 'Separator, Line' CategoryUnicode Characters in the 'Separator, Paragraph' Categoryです。

関連する問題