文字列変数から文字を削除しようとしています。sed
次のようにすればうまくいきます:
MYVAR=--23ho02123ware38384you443d34o3434ingtod38384day-%§*#sfrf
echo ${MYVAR} | sed -e 's/[a-z][a-z0-9\-]*//g'
そして次のようになります:
--23%§*#
それが私が探しているものです。文字列は文字で始まり、文字、数字、ダッシュ (-) のみで構成されている必要があります。bash
文字列置換でこれを実現する方法はありますか?
MYVAR=${MYVAR/[a-z][a-z0-9-]*/ }
いくつかの組み合わせを試してみましたが、どれも期待通りには機能しませんでした。
答え1
正規表現と同等のものを得るには、ksh 拡張 glob 演算子 (そのサブセットはbash
withshopt -s extglob
およびzsh
withで使用可能) を使用する必要があります (ただし、構文は異なります。ここではと同等のものは次のようになります)。set -o kshglob
*(x)
x*
shopt -s extglob # for bash
# set -o kshglob # for zsh
printf '%s\n' "${MYVAR//[[:alpha:]]*([[:alnum:]-])/}"
または、zsh
extendedglob
s の場合、 regexp と同等のものは次のように*
なります#
。
set -o extendedglob
printf '%s\n' ${MYVAR//[[:alpha:]][[:alnum:]-]#}
いくつかの注意事項:
${var/pattern/replacement}
最初の出現のみを置き換えます。すべての出現を置き換えるには、 を使用します(のコマンドのフラグ${var//pattern/replacement}
と同様)。g
sed
s
- 置換文字をスペース文字にした場合、空の文字列に置き換えるには
${var//pattern/}
(または) を使用します。${var//pattern}
echo
任意の文字列を出力するために使用したくない- ただし
zsh
、リストコンテキストでの変数展開は引用符で囲む必要がある sed
変数に改行文字が含まれている場合、動作はあなたのアプローチとは異なります。[a-z]
a
は、との間の文字(一部のツールでは照合要素)に一致します。z
この文字のリストは、ロケール、システム、ツールによって異なります(たとえば、GNUシステムのロケールで[a-z]
は、、、に一致しますが、 には一致しません)。これには通常、英語のアルファベットの26個の小文字が含まれますが、必ずしもそうとは限りません。には、 と見なされる文字(または照合要素)が含まれます。bash-4.3
en_GB.UTF-8
A
X
é
Ẃ
Z
[[:alpha:]]
アルファベット順(大文字と小文字を区別しない) をロケールで使用します。26 個の英語の文字のみを一致させたい場合は、[abcdefghijklmnopqrstuvwxyz]
ロケールをC
(LC_ALL=C
) に固定し、小文字の英語の文字のみに[a-z]
または を使用し、すべての英語の文字に/ を使用します。[[:lower:]]
[a-zA-Z]
[[:alpha:]]
[a-z0-9\-]
はsed
バックスラッシュ文字と一致しないため、[a-z0-9-]
代わりに を使用します (-
文字どおりに解釈されるためには、 が最初または最後にある必要があります)。