これは、先読みの助けを借りて正規表現で行うことができます。しかし、これは最適ではありません。マッチごとにいくつかの括弧のグループを「再解析」するからです。実際のパーサーを使用すると、文字列の読み取り/解析が 1 回だけになり、より効率的になります。
例 ( ideone ):
using System;
using System.Text.RegularExpressions;
public class Example
{
public static void Main()
{
var re = @"(?x) # ignore spaces and comments
(?= # lookahead (zero width)
(
\( # first (
(?:
(?<open> \( )* # open++
[^()]+
(?<-open> \) )* # open--
)+
\) # last )
(?(open)(?!)) # fail if unblanaced: open > 0
)
)
\( # eat a (, to advance the match a char";
var str = "a + ((b + (c + d)) + (e + f)) + (x + ((y) + (z)) + x)";
var m = Regex.Matches(str, re);
Console.WriteLine("Matched: ");
foreach (Match i in m)
Console.WriteLine(i.Groups[1]);
}
}
出力:
Matched:
((b + (c + d)) + (e + f))
(b + (c + d))
(c + d)
(e + f)
(x + ((y) + (z)) + x)
((y) + (z))
(y)
(z)