web-dev-qa-db-ja.com

「x」文字未満のテキストファイルのすべての行を削除するにはどうすればよいですか?

'x'文字より少ないテキストファイルのすべての行を削除するにはどうすればよいですかOR数字OR記号?awk 'length($0)>'スペースが含まれるため。

8
Aeden Thomas

n未満のグラフィックシンボルを含む行を削除するとします。

awk -v n=5 '{ line = $0; gsub("[^[:graph:]]", "") } length >= n { print line }'

これにより、[[:graph:]]に一致しないすべての文字が削除されます。残っている文字列の長さがn以上の場合、(変更されていない)行が出力されます。

nの値はコマンドラインで指定します。

[[:graph:]][[:alnum:][:punct:]]と同等で、[[:alpha:][:digit:][:punct:]]と同じです。 [[:print:]]とほぼ同じですが、スペースとは一致しません。

[^[:graph:]]の代わりに、[[:blank:]]を使用してすべてのタブまたはスペースを削除することができます。

sedを使用すると、上記のawkコードに従って、ほとんど文字通り、

sed -e 'h; s/[^[:graph:]]//g' \
    -e '/.\{5\}/!d; g'

または、簡略化(空白以外の文字のみを数える)、

sed -e 'h; s/[[:blank:]]//g' \
    -e '/...../!d; g'

これは最初に、現在の行をhを使用してホールドスペースに保存します。次に、s///gを含む行のすべての非グラフ文字(または2番目のバリエーションの空白文字)を削除します。その行に含まれる文字が5文字未満の場合(これを任意の数に変更するか、2番目のバリエーションのドットの数を変更します)、その行は削除されます。そうでない場合、保存された行はgを使用してホールドスペースからフェッチされ、(暗黙的に)印刷されます。

13
Kusalananda
_sed -e 's/[^[:space:][:cntrl:]]/&/20' -e t -e d < file
_

空白以外の非制御文字が少なくとも20含まれるfileの行を出力します(_[[:graph:]]_または_[[:alnum:][:punct:]]_も参照してください。説明に含める/除外する文字が明確でないため、注意してください)一部のシステムでは、非改行文字はgraphではなくspaceに含まれています)。

考えは、それが非空白文字/制御文字の20番目の出現をそれ自体で置換しようとすること(_&_)であり、その置換が成功した場合は分岐し(t)、したがってdアクションをスキップします(削除する)。

awkを使用すると、次のことができます。

_awk 'gsub(/[^[:space:][:cntrl:]]/, "&") >= 20' < file
_

gsub()が行った置換の数を返すという事実に依存しています。

grepの場合:

_grep -E '^([[:space:][:cntrl:]]*[^[:space:][:cntrl:]]){20}' <  file
_

(_(.*[^[:space:][:cntrl:]]){20}_も機能しますが、より高価になります)。

7

これにより、10文字以下で10文字未満の行が削除されます:

sed -E '/^.{1,11}$/d' filename

OR

sed -r '/^.{1,11}$/d' filename  

スペースをトリミングしたい場合は、以下を使用できます。

sed -E 's/^[[:space:]]*//g;s/[[:space:]]*$//g;/^.{1,11}$/d' filename

インプレース(ファイル内で直接)削除する場合は、-iオプションを使用して削除します。

Raku(néePerl6)の使用

raku -ne '.put if chars( S:g/\s// ) >= 10;'  filename

または

raku -ne '.put unless chars( S:g/\s// ) < 10;'  filename

または

raku -ne '.put unless chars( S:g/\W// ) < 10;'  filename

または

raku -ne '.put unless chars( S:g/<ws>// ) < 10;'  filename

簡単に言うと、Raku/Perl6では、「capital-S」のS///演算子を使用して、不要な文字(空白など)を含まない結果の文字列を生成します。結果の文字列の文字は、chars関数で「n」と比較されます(例として10を使用)、そして最後に-ブール値が満たされている場合、.putは元の行をそのまま返します。

注1: "S ///はs ///演算子と同じセマンティクスを使用しますが、元の文字列をそのまま残し、$ /($ /の代わりに結果の文字列を返します。 s ///と同じ値)」

https://docs.raku.org/language/regexes#S///_non-destructive_substitution

注2:Raku/Perl6では、:g(「グローバル」の)のような正規表現修飾子は副詞と呼ばれ、(通常)S///またはs///演算子の頭のSまたはsの直後に配置されます。

注3:Raku/Perl6の.ドットは、トピック変数$_のメソッドを呼び出すために使用されるため、コード.putの最初の「Word」は、基本的に$_.putの省略形です。

https://docs.raku.org/language/5to6-nutshell#-%3E_Method_calls

注4:Raku/Perl6には、コマンドラインフラグのセットがはるかに制限されています。 -eフラグ( "execute")は、コマンドラインでRaku/Perl6コードを実行します。 -nフラグはRaku/Perl6コードを行ごとに実行します。つまり、入力ファイルの各行に対して一度に1行ずつ実行し、結果を返します。 2つのフラグは-neフラグに組み合わせることができますが、それとは関係なく、-eフラグは最後に来る必要があります。

https://docs.raku.org/language/5to6-nutshell#Command-line_flags
https://github.com/rakudo/rakudo/wiki/Running-rakudo-from-the-command-line

1
jubilatious1
_ Perl -n -e 'print if tr/!-\176// > 38'
_

ここで、38はスペース以外の文字の数です。

特定のリストについてスペース以外の文字を探している場合は、tarの最初の2つの/の間に置いてもかまいません。個別に、または「-」で範囲を指定:例.

_ tr/A-Za-z0-9//
_

あなたが必要な場合-それらの1つになるには、最初に-を置きます。

/にする必要がある場合は、_\057_としてエンコードします。

_tr/A-Za-z0-9\057+//          # match characters in Base64
_

ゴリー詳細

_Perl -e_は、Perlプログラムがコマンドラインにあることを意味します。
_Perl -n -e_は、プログラムを入力の各行で繰り返す、つまりPerlでラップすることを意味しますwhile (<>) { your code here }

Perlは反復しながら、$ _と呼ばれるメタ変数に入力を取り込みます。

これは、ほとんどのコマンド(printおよびtrを含む)のデフォルトのターゲットでもあります。

_command if condition_は、「if(condition){command}」のPerlイディオムです。

_tr///_はtransliteration演算子です。 _tr/ABC/abc/_は、すべてのAをaに、Bをbに、Cをcに変更することを意味します。 _-_演算子は範囲を意味するため、_tr/A-Z/a-z/_はアルファベット全体を意味します。 2番目のフィールドがnullの場合、文字列は変更されません。 tr ///演算子の戻り値は、一致した文字の数です。

太ったコードに吹き飛ばされ、このコードは次のようになります

_ $textstart = "!";    # first character after space
 $textend = "\176";   # last printable character in octal; dec 126 or 0x7E 
 $textrange = $textstart . "-" . $textend; 

 while (defined ($_ = <STDIN>) ) {    # while able to suck a line from STDIN into $_

     if ( {$_ =~ tr/$textrange//}     # count desired characters within textrange 
                                  > 38  )   # compare to 38
     {                                # start if block
           print $_;                  # If valid, print raw input
     }                                # end if block   

 }  # end while
_