SEDチャレンジ、中括弧を含む文字列の集計

SEDチャレンジ、中括弧を含む文字列の集計

私は数時間sedを使用してテキストの特定の文字列パターンを集計しようとしましたが、解決策が見つかりませんでした。私はあなたが何をすべきかを知っていることを願っています! ?

  • 私のターゲットのテキストは文字列のみで構成されています(見えない\ tは存在しません)。
  • (TAB)を含みますが、少なくとも2つは互いに隣接し、最大8つは互いに隣接する文字列部分を見つけて単一の(TAB)項目に置き換えたいと思います。

  • 検索は、bashスクリプトを含むシェルファイルで実行する必要があります。

例:

#!/bin/bash

text="Column One(TAB)(TAB)(TAB)Column Two(TAB)(TAB)Column three(TAB)Column4"

modText=`echo $text | sed 's/([(]\{1\}TAB[)]\{1\})\{2,8\}/(TAB)/g'`
  • 私はいくつかのバージョンのsed-commandを試しましたが、上記はそのうちの1つだけです。私の最初の考えはmodText = `echo $ text | sed 's/\(TAB\)\{1\})\{2,8\}/(TAB)/g'` でした。

あなたが私を助けることができれば良いでしょう。解決策はそれほど遠くないように感じますが、もはやアイデアはなく、私の研究でもうまくいきませんでした。 :-S


テキストの例

「第1列(TAB)(TAB)(TAB)第2列(TAB)(TAB)第3列(TAB)第4列」

私の検索基準は、「最初の列」と「3番目の列」の間に表示される最初の2つ(TAB)グループと一致します。

結果次のようにする必要があります。

「第1列(TAB)第2列(TAB)第3列(TAB)第4列」

答え1

「最大8」条項がどのように適用されるかはわかりませんが、素朴なアプローチは次のとおりです。

sed 's/\((TAB)\)\{2,8\}/(TAB)/g'

答え2

隣接する s が 8 個より多い場合、交換が発生してはならないという意味であれば、(TAB)次のようにすることができます。

sed '
   s/_/_u/g; # escape _
   s/|/_p/g; # escape |
   s/(TAB)/|/g; # use a single character in place of (TAB)
   s/.*/<&>/; # add leading and trailing non-| character
   s/\([^|]\)|\{2,8\}\([^|]\)/\1|\2/; # replace up to 8 | provided
                                      # they are not preceded nor followed
                                      # by |
   s/.\(.*\)./\1/; # undo wrapping
   s/|/(TAB)/g;    # undo replacement
   s/_p/|/g;s/_u/_/g; # undo escaping'

Perl のような正規表現をサポートしている場合sed(たとえばssed) ツアー演算子を使用できます。

ssed -R 's/(?<!\(TAB\))(\(TAB\)){2,8}(?!\(TAB\))/(TAB)/g'

または直接perl使用してください。

perl -lpe 's/(?<!\(TAB\))(\(TAB\)){2,8}(?!\(TAB\))/(TAB)/g'

AT&T(ast-open) は / オプションをsed使用して拡張正規表現をサポートします。-A-X改善一つある否定的な演算子(x!)と接続会社オペレーター( x&y)。そこから(.{5}&(\(TAB\))!)5つの文字シーケンスを一致させます。いいえ (TAB)。したがって、sed次のことができます。

sed -A '
  :1
    s/(^.{0,4}|.{5}&(\(TAB\))!)(\(TAB\)){2,8}(.{0,4}$|.{5}&(\(TAB\))!)/\1(TAB)\4/
  t1'

関連情報