Как исключить совпадение с регулярным выражением во вложенных скобках - PullRequest
3 голосов
/ 06 июня 2019

У меня есть такой текст:

UseProp1?(Prop1?Prop1:Test):(UseProp2?Prop2:(Test Text: '{TextProperty}' Test Reference:{Reference}))

Я пытаюсь использовать регулярное выражение в c # для извлечения вложенных сегментов if / else.

Чтобы найти '?'Я использовал:

Шаблон 1: \?\s*(?![^()]*\))

и для поиска ':' Я использовал:

Шаблон 2: \:\s*(?![^()]*\))

Это прекрасно работает, когда есть один уровень скобок, но не при их вложении.

Я использовал этот онлайн-инструмент для упрощения тестирования: http://regexstorm.net/tester (и вставьте шаблон-1 и введитесверху)

Как видите, он выделяет два матча, но я хочу только первый.Вы также заметите, что первые круглые скобки пропущены, но не следующие со вложенными уровнями

Я ожидаю, что список совпадений будет:

1) UseProp1

2)(Prop1? Prop1: Test) :( UseProp2? Prop2: (Test Text: '{TextProperty}' Ссылка на тест: {Reference}))

То, что я получаю сейчас:

1) UseProp1

2) (Prop1? Prop1: Test) :( UseProp2

3) Prop2: (Test Text: '{TextProperty}' Ссылка на тест: {Reference}))

Ответы [ 2 ]

0 голосов
/ 07 июня 2019

Расширяя комментарий @ bobble bubble , вот мое регулярное выражение:

Это захватит первый слой троичных функций.Группы захвата: $ 1 является условным, $ 2 - истинным предложением, а $ 3 - ложным предложением.Затем вам нужно будет сопоставить регулярные выражения для каждого из них, чтобы перейти вниз по дереву:

((?:\((?>\((?<c>)|[^()]+|\)(?<-c>))*(?(c)(?!))\))+|\b[^)(?:]+)+\?((?:\((?>\((?<c>)|[^()]+|\)(?<-c>))*(?(c)(?!))\))+|\b[^)(?:]+)+\:((?:\((?>\((?<c>)|[^()]+|\)(?<-c>))*(?(c)(?!))\))+|\b[^)(?:]+)+

Код в тестере

При этом, если выОценивая математику и в этих выражениях, может оказаться более полезным использовать компилятор времени выполнения, чтобы выполнить всю тяжелую работу за вас. Этот ответ поможет вам спроектировать в этом направлении, если вы того пожелаете.

0 голосов
/ 06 июня 2019

Если я правильно понимаю, и мы хотим захватить только два перечисленных формата, мы можем начать с простого выражения, используя чередование, а затем изменим его отсеки, если захотим:

UseProp1|(\(?Prop1\?Prop1(:Test)\)):(\(UseProp2\?Prop2):\((Test\sText):\s+'\{(.+?)}'\s+Test\sReference:\{(.+?)}\)\)

Демонстрация

Тест

using System;
using System.Text.RegularExpressions;

public class Example
{
    public static void Main()
    {
        string pattern = @"UseProp1|(\(?Prop1\?Prop1(:Test)\)):(\(UseProp2\?Prop2):\((Test\sText):\s+'\{(.+?)}'\s+Test\sReference:\{(.+?)}\)\)";
        string input = @"UseProp1
(Prop1?Prop1:Test):(UseProp2?Prop2:(Test Text: '{TextProperty}' Test Reference:{Reference}))
";
        RegexOptions options = RegexOptions.Multiline;

        foreach (Match m in Regex.Matches(input, pattern, options))
        {
            Console.WriteLine("'{0}' found at index {1}.", m.Value, m.Index);
        }
    }
}

RegEx

Если это выражение было нежелательным, и вы хотите изменить его, посетите этоссылка на regex101.com .

Схема RegEx

jex.im визуализирует регулярные выражения:

enter image description here

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...