Сложное регулярное выражение с пользовательским построителем формул

#regex #vb.net #string #.net-2.0

#регулярное выражение #vb.net #строка #.net-2.0

Вопрос:

У меня есть строка, которая выглядит так — MVAL("A","01-01-1900") MVAL(B,"01-01-1900") MVAL("C") MVAL(D) . Теперь я хочу извлечь B и D из этого, используя регулярное выражение, потому что это первый параметр, и вокруг него нет кавычек в обеих перегруженных версиях функций. Во-вторых, потому MVAL что функция является перегруженной функцией с двумя версиями, такими как MVAL("A") и MVAL(B,"01-01-1900") как я найду, какая версия функции используется.

Пожалуйста, помогите. Я использую System.Text.RegularExpressions.Regex метод.

Ответ №1:

Можно ли с уверенностью предположить, что после первого параметра никогда не будет запятой, если за ним не следует второй параметр? Если это так, это должно быть все, что вам нужно:

 string s = @"MVAL(""A"",""01-01-1900"") MVAL(B,""01-01-1900"") MVAL(""C"") MVAL(D)";

foreach (Match m in Regex.Matches(s, @"MVAL((w )(,)?"))
{
  Console.WriteLine("First param: {0}nHas second param? {1}n",
                    m.Groups[1], m.Groups[2].Success);
}
  

вывод:

 First param: B
Has second param? True

First param: D
Has second param? False
  

Если нет запятой, общее совпадение все равно будет успешным, потому что запятая необязательна. Но, поскольку вторая группа захвата не участвовала в сопоставлении, ее Success свойство имеет значение False .

Это регулярное выражение также предполагает, что в строке никогда не будет пробелов, как в вашем примере. Это регулярное выражение допускает пробелы между элементами синтаксиса:

 @"MVALs*(s*(w )s*(,)?
  

Комментарии:

1. Что, если у меня есть три параметра для MVAL, будет ли что-то вроде этого работать MVAL((w )(,)(w )(,)(w )

2. Ну, это соответствовало MVAL(A,B,C) бы, но нет MVAL("A","B","C") .

Ответ №2:

Похоже, вы просто хотите сопоставить текст MVAL( , за которым следует буква (или, возможно, идентификатор). Попробуйте это:

 MVAL(([A-Z])
  

Первая часть, MVAL( , соответствует префиксу. Затем у нас есть текст, заключенный в круглые скобки : ([A-Z]) . Скобки сообщают механизму регулярных выражений «захватить» любой текст, содержимое которого будет соответствовать, что означает, что мы можем использовать его позже. Вот почему нам пришлось экранировать открывающее выражение с обратной косой чертой в префиксе.

[A-Z] Шаблон соответствует любому символу между A и Z . Сюда входят все заглавные буквенные символы. Затем мы указываем движку регулярных выражений игнорировать регистр, чтобы он также соответствовал всем строчным символам.

 Dim regex = new Regex("MVAL(([A-Z])", RegexOptions.IgnoreCase)
Dim match = regex.Match(input)
Dim parameter = match.Groups(1)
  

Если вы хотите сопоставить любой допустимый идентификатор, а не только одну букву, попробуйте это вместо:

 MVAL(([A-Z_][A-Z0-9_]*)
  

Эта захваченная часть будет соответствовать любой букве или символу подчеркивания, за которым следует ноль или более (обозначаемых * ) букв, цифр или символов подчеркивания.

Комментарии:

1. Осторожно, [A-z] также соответствует некоторым не-буквам между ASCII Z и ASCII a. Лучше использовать [A-Z] с Regex.IgnoreCase .

2. Да, но как мне определить, всегда ли это регулярное выражение выбирает первый параметр.

3. @SohamDasgupta: Каков результат? Это не соответствует?