如何在管道命令中使用条件语句?

如何在管道命令中使用条件语句?

正在处理的数据将遵循特定的模式。在这种情况下,我想隔离第三列中找到的所有字符,并返回在“-”但前提是该分隔符存在于列中。否则它不应该返回任何内容。

eval $A=$(echo $1 | awk -F"." '{print $3}' | cut -d\- -f2-)

第一条awk语句将字符串分解为

111
222
333-ab3-On21-2

cut命令打印第一个“-”之后的字符。

字符串 1 111.2222.333-ab3-On21-2返回期望的结果:

ab3-On21-2

字符串2 111.2222.334返回不需要的结果:

333

字符串的最后一部分中不存在分隔符"-",在这种情况下如何更改此代码以返回 0 或“”?

答案1

我不确定你从哪里得到“条件”,因为你的陈述中没有任何条件。没有awk -F- {print}做任何有用的事情;只是将输入传递到输出。

但是,您可以使用表达式执行您想要的操作sed,以简化整个管道:

sed -n 's/.*\.[^-]*-\(.*\)/\1/p'

-n和意味着p它只会打印与表达式匹配的字符串。

该表达式将删除直到最后一个.,然后删除第一个之前的所有内容-

所以:

% echo 111.2222.333-ab3-On21-2 | sed -n 's/.*\.[^-]*-\(.*\)/\1/p'
ab3-On21-2
% echo 111.2222.333 | sed -n 's/.*\.[^-]*-\(.*\)/\1/p'           
% 

如果您的输入更复杂(例如可能有四个.分隔字段),那么模式可能需要更聪明一些。

sed -n 's/.*\.[^-]*-\([^\.]*\).*/\1/p'

例如

% echo 111.2222.333-ab3-On21-2.999 | sed -n 's/.*\.[^-]*-\([^\.]*\).*/\1/p'
ab3-On21-2

答案2

grep -o -P '[^.]*\.[^.]*\.[^-]*-\K.*'

起初我想到使用正向后查找,但它不适用于非固定长度的正则表达式。然后,我做了一些谷歌搜索,发现 Perl 有\K重置匹配的令牌。

例子:

grep -o -P '[^.]*\.[^.]*\.[^-]*-\K.*' <<< 111.222.333-ab3-0n21-2

ab3-0n21-2
grep -o -P '[^.]*\.[^.]*\.[^-]*-\K.*' \
  <<< '128-2sd83--.3 832 @!@!# 323.7 dskj ...-ab3-0n21-2'

ab3-0n21-2

答案3

cut将, 与-s(或) 选项一起使用--only-delimited

printf '%s\n' '111.2222.333-ab3-On21-2' '111.2222.334' | 
cut -d '.' -f 3 | cut -d '-' -sf 2-

输出:

ab3-On21-2

相关内容