0

(arg1)、、、など(arg1, arg2)に一致する正規表現を作成するにはどうすればよいですか(arg1, arg2, xarg, zarg)。すべての名前は常に記号で始まるASCII文字列[A-Za-z]です。これが私が試したことです:"("[A-Za-z][a-z0-9]*(,)?([A-Za-z][a-z0-9]*)?")"。ありがとう!

注:正規表現はで機能する必要がありますflex

4

2 に答える 2

1

そんな感じ?

>>> import re
>>> s = '''Could you explain, please, how can I make regex that will match (arg1), (arg1, arg2), (arg1, arg2, xarg, zarg), etc. Every name is an ASCII string which always starts with symbol [A-Za-z]. Here is what I've tried: "("[A-Za-z][a-z0-9]*(,)?([A-Za-z][a-z0-9]*)?")". Thanks!'''
>>> re.findall(r'\([A-Za-z]?arg[0-9]?(?:, [A-Za-z]?arg[0-9]?)*\)', s)
['(arg1)', '(arg1, arg2)', '(arg1, arg2, xarg, zarg)']
于 2012-10-21T23:39:34.523 に答える
1

flex がここで適切なツールかどうかはわかりません。通常、そのような入力を個別のトークンに分割するために使用するからです。しかし、それは確かに可能です:

"("[[:alpha:]][[:alnum:]]*(,[[:alpha:]][[:alnum:]]*)*")"

それは一致(arg1) (arg1,arg2)しますが、一致しません( arg1 )または(arg1, arg2). どこでもスペースを無視したい場合は、少し冗長になります。

この種のものは、lex 定義を使用すると、はるかに読みやすくなります。

ID      [[:alpha:]][[:alnum:]]*

%%

"("{ID}(","{ID})*")"

または、スペース マッチングを使用:

/* Make sure you're in the C locale when you compile. Or adjust
 * the definition accordingly. Perhaps you wanted to allow other 
 * characters in IDs.
 */
ID      [[:alpha:]][[:alnum:]]*
/* OWS = Optional White Space.*/
/* Flex defines blank as "space or tab" */
OWS     [[:blank:]]*
COMMA   {OWS}","{OWS}
OPEN    "("{OWS}
CLOSE   {OWS}")"

%%

{OPEN}{ID}({COMMA}{ID})*{CLOSE}  { /* Got a parenthesized list of ids */

最後の注意: これも一致しません()。少なくとも 1 つの ID が必要です。それも含めたい場合は、括弧の間の部分をオプションにすることができます:

{OPEN}({ID}({COMMA}{ID})*)?{CLOSE}  { /* Got a parenthesized        */
                                      /* possibly empty list of ids */
于 2012-10-22T03:00:17.803 に答える