3

次のようなテキストがあります。

(something1)something2

ただし、something1 と something2 には、次のような括弧が含まれている場合もあります。

(some(thing)1)something(2)

something1変数に(内部括弧がある場合はそれを含めて)抽出したい。テキストは常に開き括弧で始まると期待できるので、最初の括弧を正しい閉じ括弧に一致させ、中間を抽出することができることを望んでいます。

私がこれまでに試したことはすべて、間違った終わりの括弧に一致する可能性があります。

4

4 に答える 4

4

perl をお持ちの場合:

perl -MText::Balanced -nlE 'say [Text::Balanced::extract_bracketed( $_, "()" )]->[0]' <<EOF
(something1)something2
(some(thing)1)something(2)
(some(t()()hing)()1)()something(2)
EOF

印刷します

(something1)
(some(thing)1)
(some(t()()hing)()1)
于 2013-05-31T21:18:53.593 に答える
2

あなたはperlでそれを行うことができます:

echo "(some(thing)1)something(2)" | perl -ne '$_ =~ /(\((?:\(.*\)|[^(])*\))|\w+/s; print $1;'
于 2013-05-31T21:13:41.240 に答える
1

awk出来る:

#!/bin/awk -f
{
   for (i=1; i<=length; ++i) {
      if (numLeft == 0 && substr($0, i, 1) == "(") {
         leftPos = i
         numLeft = 1
      } else if (substr($0, i, 1) == "(") {
         ++numLeft
      } else if (substr($0, i, 1) == ")") {
         ++numRight
      }
      if (numLeft && numLeft == numRight) {
         print substr($0, leftPos, i-leftPos+1)
         next
      }
   }
}

入力:

(something1)something2
(some(thing)1)something(2)

出力:

(something1)
(some(thing)1)
于 2013-05-31T21:17:25.630 に答える
1

これは明らかに正規表現では不可能なことなので、文字を 1 つずつピックアップすることにしました。

    first=""
count=0
while test -n "$string"
do
    char=${string:0:1}  # Get the first character
    if [[ "$char" == ")" ]]
    then
        count=$(( $count - 1 ))
    fi
    if [[ $count > 0 ]]
    then
        first="$first$char"
    fi
    if [[ "$char" == "(" ]]
    then
        count=$(( $count + 1 ))
    fi
    string=${string:1}  # Trim the first character
    if [[ $count == 0 ]]
    then
        second="$string"
        string=""
    fi
done
于 2013-05-31T21:08:08.870 に答える