[0-9]*が数字なしでどこにも一致するのはなぜですか?

[0-9]*が数字なしでどこにも一致するのはなぜですか?

したがって、コマンドは次のようになります。

echo "abc 123" | sed "s/[0-9]*/h/g"

私が得た結果は次のとおりです。

hahbhch h

この出力をどのように取得しますか?

私が望む出力はabc hです。

このコマンドで得られるものは次のとおりです。

echo "abc 123" | sed "s/[0-9][0-9]*/h/g"

誰かがこれを説明できますか?

答え1

これは*、ゼロ以上の一致をできるだけ早く意味します。gフラグなしでコマンドを実行すると(つまりsed、最初の置換後に停止することを意味します)、出力が得られますhabc 123。左から右に読み始めるのに一致しないので、行の先頭にaのみ一致し、そこで停止するからです。

global( g) フラグを使用すると、文字列の残りの部分と一致しようとし、*他のものと一致できない場合は空の文字列と一致するため、hより多くの数字と一致できない場合は1つずつ配置されます。

2番目の試みは次のとおりですsed "s/[0-9]\+/h/"+一つ以上一致します。つまり、置換する数値が見つからない場合は、空の文字列と一致しません。

答え2

答えは、sedで正規表現がどのように処理されるかに関するものです。正規表現またはREは非常に複雑になる可能性があり、それを使用する機能と構文の複雑さの間にバランスがあります。さまざまなプログラミング言語は、サポートしたい機能と複雑さについてさまざまな選択肢を提供します。 Sedは非常に強力で、思ったより少し複雑です。答えを得るには、*は前のトークンのゼロ以上のインスタンスシーケンスと一致します。あなたの場合、以前のトークンはランダムな数字を意味する[0-9]です。 Sedは、入力文字列の各文字の前後に長さ0の数値文字列があることを確認します。慣れるまではやや反直観的なようです。この問題を解決する一般的な方法は、/[0-9][0-9]*/ を使用することです。これは、数字の後にゼロ個以上の数字が続くと解釈されます。別の解決策は*を+に置き換えることです。 + 1つ以上の古いトークンシーケンスと一致します。したがって、完全なコマンドは次のようになります。

echo "abc 123" | sed "s/[0-9]+/h/g"

オンラインマニュアル(google man sedのみを使用)を使用してsedコマンドについて読むことができます。または、システムにマニュアルがインストールされている場合は、man sedコマンドを実行してください。

関連情報