条件部分的awk变量?

时间:2017-03-07 19:17:57

标签: awk

当第一列中的数字与第五列和第六列中的数字相同时我需要过滤文件而我写了

awk -F, 'gensub(/[^0-9]/, "", "G", $1) == gensub(/[^0-9]/, "","G", $5) &&
         gensub(/[^0-9]/, "", "G", $1) == gensub(/[^0-9]/, "","G", $6)'

对我来说运行得很好,文件足够小,不会出现问题,但我仍然想知道:是否可以将gensub(/[^0-9]/, "", "G", $1)分配给变量,这样我就不需要进行两次替换了?

编辑: 123.4.5,B,C,D,12-345,1-2-34/5 这是我们想要保留的一条线。因为丢弃非数字字符后的第1,第5和第6列是12345。 123,B,C,D,12-345,1-2-34/5 这是我们要过滤掉的一行。

4 个答案:

答案 0 :(得分:2)

是的,任何单个表达式在模式语句中都有效 (参考Standard Grammar)。

$ printf 'one\ntwo\nthree\n' | awk '(var=gsub(/e/,""))&&var==2'
thr

答案 1 :(得分:2)

另一种选择是

 awk '{a[1]=$1; a[5]=$5; a[6]=$6; 
       for(k in a) sub(/[^0-9]/,"",a[k])} 
      a[1]==a[5] && a[1]==a[6]' file

甚至

awk 'BEGIN{a[1]; a[5]; a[6]} 
          {for(k in a) 
             {a[k]=$k; sub(/[^0-9]/,"",a[k])}} 
     a[1]==a[5] && a[1]==a[6]' file

答案 2 :(得分:0)

你可以试试这个 -

awk -F, '{kk=gensub(/[^0-9]/, "", "G", $1); if(kk == gensub(/[^0-9]/, "","G", $5) && kk == gensub(/[^0-9]/, "","G", $6)) print $0}'

答案 3 :(得分:0)

你真的应该发布一些样本输入和预期输出来获得最好的答案,但它就像你要求的东西一样:

awk -F, '(k=gensub(/[^0-9]/, "", "G", $1)) == gensub(/[^0-9]/, "","G", $5) &&
         k == gensub(/[^0-9]/, "","G", $6)'

与更明显和简洁相比,这当然不是一个好方法:

awk -F, '
function f(s) { return gensub(/[^0-9]/, "", "g", s) }
{ k = f($1) }
f($5)==k && f($6)==k
'

但这可能是一种荒谬的方法,具体取决于输入数据的样子。