2014-03-05 47 views
2

我的工作是使用AWK对match lines with at least 2 digits and at least 2 letters in any order(某些字母用数字分隔)。AWK与至少2位数字匹配的行和至少2个字母的任意顺序

这是我为sample.txt:

1 
12 
123 
1234 
12345 
123456 

1a 
b23 
3c4d 
e5f67 
gj34qz 

我AWK的版本是GNU awk中4.0.1(Ubuntu Linux操作系统)。

我一直在试图做这种方式:

awk '/[0-9]{2,}/ && /[a-z]{2,}/' sample.txt

awk '/[[:digit:]]{2,}/ && /[[:lower:]]{2,}/' sample.txt

,但它不工作正确的方式(它只能检测连续字符串)例如它跳过:

3c4d

e5f67

回答

4

.*之间允许的字符:

awk '/[0-9].*[0-9]/ && /[a-zA-Z].*[a-zA-Z]/' 

正是两个字母:

awk '/[0-9].*[0-9]/ && /^[^a-zA-Z]*[a-zA-Z][^a-zA-Z]*[a-zA-Z][^a-zA-Z]*$/' 
+0

+1我现在觉得自己像个白痴。 ':)' –

+0

+1我的回答(几乎)确切地说:'awk'/ [[:数字:]]。* [[:数字:]]/&& [[:alpha::]]。* [[: :]] /'' –

+0

这是工作感谢,我是如此亲密:)。也许你知道一个不同的场景,如果我们想要捕捉至少两位数字和只有两个字母(再次命令无关)的小改变? – mike

1

可以使用gsub函数的返回值来计算的许多数字和字母是如何存在于行。

gsub函数返回进行的替换次数。所以,你可以这样做:

awk '{l=$0;if(gsub(/[[:digit:]]/,x)>=2 && gsub(/[[:lower:]]/,x)>=2) print l}' file 

我们店因为gsub运行原线被修改后的变量l行。我们检查gsub的返回值为>=2。如果两个条件都成立,我们会打印该行。

有了您的样本数据,输出:

$ awk '{l=$0;if(gsub(/[[:digit:]]/,x)>=2 && gsub(/[[:lower:]]/,x)>=2) print l}' file 
3c4d 
e5f67 
gj34qz 
+0

**注:**使用此解决方案,如果您的范围更改为每个类型的6个或更多字符。然后你可以简单地将'if ='条件修改为'> = 6',但是对于当前的情况[凯文的答案](http://stackoverflow.com/a/22209725/970195)应该很好。 –

相关问题