如何使用sed替换TSV中的模式?

时间:2014-07-29 00:01:38

标签: regex sed

我有一个TSV文件,其中char *用作空标识符,我想删除它,文件如下所示:

Foo Foo foo FOO
Bar *   *   *
*Bar    Foo*    Foo * Bar   Foo bar
*   *   Bar Foobar

如果我使用s/(^| )\*( |$)/\1\2/g给出此输出:

Foo Foo foo FOO
Bar     *   
*Bar    Foo*    Foo * Bar   Foo bar
*   Bar Foobar

匹配一个是,一个不是,如果它们被TABS包围,我该怎么做才能替换所有这些?

所需的输出应如下所示:

Foo Foo foo FOO
Bar         
*Bar    Foo*    Foo * Bar   Foo bar
        Bar Foobar

3 个答案:

答案 0 :(得分:3)

由于不太清楚标签是什么,让我们尝试使用|作为字段分隔符:

$ cat a
Foo|Foo|foo|FOO
Bar|*|*|*
*Bar|Foo*|Foo * Bar|Foo bar
*|*|Bar|Foobar

因此我们可以使用awk

$ awk 'BEGIN{FS=OFS="|"}{for (i=1; i<=NF; i++) if ($i=="*") $i=""}1' a
Foo|Foo|foo|FOO
Bar|||
*Bar|Foo*|Foo * Bar|Foo bar
||Bar|Foobar

这会遍历所有字段并将它们空白(将它们设置为空),以防它们的值完全为*

注意:要使此解决方案能够处理您的示例输入,只需替换字段分隔符的定义:从BEGIN{FS=OFS="|"}BEGIN{FS=OFS="\t"}

答案 1 :(得分:0)

你可以试试下面的perl comman,

$ perl -pe 's/(\W|^)\*\t\*/\1/g;s/\t\*$//g' file
Foo Foo foo FOO
Bar         
*Bar    Foo*    Foo * Bar   Foo bar
        Bar Foobar

答案 2 :(得分:0)

授予他们分隔标签:

sed -r 's@([^\t])[*]@\1__0x2A__@g; s@[*]([^\t\r])@__0x2A__\1@g; s@[*]@@g; s@__0x2A__@*@g' file

更短的:

sed -r 's@([^\t])[*]@\1\a@g; s@[*]([^\t\r])@\a\1@g; s@[*]@@g; s@\a@*@g' file

输出:

Foo     Foo     foo     FOO
Bar
*Bar    Foo*    Foo * Bar       Foo bar
                Bar     Foobar