AWK-基于正则表达式增加价值

时间:2019-04-10 19:57:58

标签: regex linux awk

我必须在Linux中使用awk添加REGEX返回的数字。

基本上来自此文件:

123john456:x:98:98::/home/john123:/bin/bash

我必须使用awk添加数字123456。 因此结果将是579

到目前为止,我已经执行了以下操作:

awk -F ':' '$1 ~ VAR+="/[0-9].*(?=:)/" ; {print VAR}' /etc/passwd

awk -F ':' 'VAR+="/[0-9].*(?=:)/" ; {print VAR}' /etc/passwd

awk -F ':' 'match($1, VAR=/[0-9].*?:/) ; {print VAR}' /etc/passwd

根据我所见,比赛根本不支持这一点。

有人有什么主意吗?

更新: 它也应该为 john123的结果-> 123 123john的结果-> 123

7 个答案:

答案 0 :(得分:2)

$ awk -F':' '{split($1,t,/[^0-9]+/); print t[1] + t[2]}' file
579

更新后的要求:

$ cat file
123john456:x:98:98::/home/john123:/bin/bash
john123:x:98:98::/home/john123:/bin/bash
123john:x:98:98::/home/john123:/bin/bash

$ awk -F':' '{split($1,t,/[^0-9]+/); print t[1] + t[2]}' file
579
123
123

答案 1 :(得分:0)

使用gawk并给出示例

awk -F ':' '{a=gensub(/[a-zA-Z]+/,"+", "g", $1); print a}' inputFile | bc

会做这份工作。 更笼统:

awk -F ':' '{a=gensub(/[a-zA-Z]+/,"+", "g", $1); a=gensub(/^+/,"","g",a); a=gensub(/+$/,"","g",a); print a}' inputFile | bc

正则表达式部分将所有字母序列替换为“ +”(例如,“ 12johnny34”变为12+34)。最后,此数学运算由bc评估。 (为安全起见,我删除了^++$开头和结尾的+号)

答案 2 :(得分:0)

您可以将[^0-9]+用作字段分隔符,而将:[^\n]*\n用作记录分隔符:

awk -F '[^0-9]+' 'BEGIN{RS=":[^\n]*\n"}{print $1+$2}' /etc/passwd

使得/ etc / passwd的内容为:

123john456:x:98:98::/home/john123:/bin/bash
john123:x:98:98::/home/john123:/bin/bash
123john:x:98:98::/home/john123:/bin/bash

这将输出:

579
123
123

答案 3 :(得分:0)

我使用awk的split()来分隔任何不包含数字的字符串的第一个字段。

split(string, target_array, [regex], [separator_array]*)

* separator_array需要gawk

$ awk -F: '{split($1, A, /[^0-9]+/, S); print S[1], A[1]+A[2]}' <<EOF
123john456:x:98:98::/home/john123:/bin/bash
123john:x:98:98::/home/john123:/bin/bash
EOF

john 579
john 123

答案 4 :(得分:0)

您可以使用

awk -F ':' '{n=split($1, a, /[^0-9]+/); b=0; for (i=1;i<=n;i++) { b += a[i]; }; print b; }' /etc/passwd

请参见online awk demo

s="123john456:x:98:98::/home/john123:/bin/bash
john123:x:98:98::/home/john123:/bin/bash"
awk -F ':' '{n=split($1, a, /[^0-9]+/); b=0; for (i=1;i<=n;i++) { b += a[i]; }; print b; }' <<< "$s"

输出:

579
123

详细信息

  • -F ':'-记录分为:个字符
  • n=split($1, a, /[^0-9]+/)-获取字段1并拆分为仅数字块,并将数字保存在a数组中,而n var包含这些块的数量
  • b=0-b将保存总和
  • for (i=1;i<=n;i++) { b += a[i]; }-遍历a数组并求和值
  • print b-打印结果。

答案 5 :(得分:0)

这里是另一种awk变体,它添加了用:分隔的第一个字段中出现的所有数字

cat file
123john456:x:98:98::/home/john123:/bin/bash
john123:x:98:98::/home/john123:/bin/bash
123john:x:98:98::/home/john123:/bin/bash
1j2o3h4n5:x:98:98::/home/john123:/bin/bash

awk -F '[^0-9:]+' '{s=0; for (i=1; i<=NF; i++) {s+=$i; if ($i~/:$/) break} print s}' file

579
123
123
15

答案 6 :(得分:0)

您也可以尝试Perl

$ cat johnny.txt
123john456:x:98:98::/home/john123:/bin/bash
john123:x:98:98::/home/john123:/bin/bash
123john:x:98:98::/home/john123:/bin/bash

$ perl -F: -lane ' $_=$F[0]; $sum+= $1 while(/(\d+)/g); print $sum; $sum=0 ' johnny.txt
579
123
123

$