echo ' 1 2 3 '|sed 's/[[:space:]]*/_/g'
我想看看_1_2_____3__
输出。相反,我将其视为_1_2_3_
输出。我究竟做错了什么??
编辑
另一件让我困惑的事情是我忘记在上面的例子中提到的,原因是:
echo ' test1 test2 ' | sed 's/[[:space:]]*/_/g'
显示这个:
_t_e_s_t_1_t_e_s_t_2_
and和...[[:space:]]
之间如何匹配?t
e
s
答案1
因为你使用*
,这意味着它匹配 0 个或多个空格。因此零个或多个空格被一个下划线替换_
。
尝试:
$ echo ' 1 2 3 ' | sed 's/[[:space:]]/_/g'
_1_2_____3__
请记住,它还[[:space:]]
匹配制表符、换行符、回车符。
笔记
答案2
您已经有了答案,但我想指出,在如此简单的场景中,无需花哨:
$ echo ' 1 2 3 ' | sed 's/ /_/g'
_1_2_____3__
如果您只想替换空格和制表符,也可以使用 [ \t] 结构:
$ echo -e " 1\t2 3 " | sed 's/[ \t]/_/g'
_1_2_____3__
答案3
这个问题明确询问了 sed,这是一个关于 sed regexp 语法的非常有效的问题。
但如果根本问题是用_
true 替换空格,这里有一个替代答案,使用“适合工作的正确工具”来翻译字符,即tr
. (man tr
)。
该命令tr abc 123
将第一个列表中的字符替换为第二个列表中相应的字符。因此,tr ' ' _
用下划线替换空格。
$ echo ' 1 2 3 ' | tr ' ' _
_1_2_____3__
为了显示更一般的情况,包括像您的示例一样的各种空白,
这里是仅翻译普通空格字符以进行比较的输出' '
:
echo ' 1 2 3 x\ny\tz' | tr ' ' _
_1_2_____3__x
y z
这是将 :space: 类的所有字符转换为 : 时的输出_
:
echo ' 1 2 3 x\ny\tz' | tr '[:space:]' _
_1_2_____3__x_y_z_
(请注意,输出末尾没有换行符 - 并且_
后面有一个z
。)
这可以显式写为tr ' \t\n' _
,它是 的缩写形式tr ' \t\n' ___
。
$ echo ' 1 2 3 x\ny\tz' | tr ' \t\n' _
_1_2_____3__x_y_z_