用于过滤不完整数据列的Sed,awk或perl

时间:2015-04-05 15:40:21

标签: regex linux perl awk sed

自然语言处理的新手。我有包含大约一百万行的csv文件。我想过滤掉不包含任何数据的第三行。例如

user1,user2, it really is  
user3,user4, oh nothin  
user5,user9, 
user7,user8,  
user9,user10,  
user11,user12, i know im in 
user13,user14, 
user15,user16, 
user17,user18, i think that might     
user19,user20, what u 
user21,user22, hmmm you never know 
user23,user24, nicee

预期输出

user1,user2, it really is 
user3,user4, oh nothin   
user11,user12, i know im in  
user17,user18, i think that might     
user19,user20, what u  
user21,user22, hmmm you never know  
user23,user24, nicee

我试过了

awk -F',+' 'NF == 3' file > file    

但是,不起作用

6 个答案:

答案 0 :(得分:1)

你可以使用这个awk:

awk -F ',[[:blank:]]*' '$NF!=""' file
user1,user2, it really is
user3,user4, oh nothin
user11,user12, i know im in
user17,user18, i think that might
user19,user20, what u
user21,user22, hmmm you never know
user23,user24, nicee

'$NF'!=""实际上是检查是否填充第3个字段的条件。

PS:你真的不能这样做:

awk -F ',[[:blank:]]*' '$NF!=""' file > file

由于输入文件和重定向文件相同,您最终会得到0字节文件。

你做得更好:

awk -F ',[[:blank:]]*' '$NF!=""' file > file.out && mv file.out file

答案 1 :(得分:1)

在Perl中,除非以逗号和空格结尾,否则会打印一行。

perl -ne'/,\s*$/ or print' file

<强>输出

user1,user2, it really is
user3,user4, oh nothin
user11,user12, i know im in
user17,user18, i think that might
user19,user20, what u
user21,user22, hmmm you never know
user23,user24, nicee

答案 2 :(得分:1)

你没有说你是否反对使用vim,但你可以在vim中加载你的文件,然后执行:

:g/,\s\+$/d

:g是vim的全局(对整个文件进行操作)

语法是:g / pattern / command

正斜杠之间的是正则表达式模式。在这里我们寻找一个逗号,然后是我们可以找到的空格(\ s +),直到我们到达行尾($)。

命令“d”表示正则表达式匹配时“删除行”。

最后:

:wq

写入文件(w)并退出(q)。

答案 3 :(得分:1)

你输入的每一行都有3个字段(因为它总是有两个逗号)所以NF总是3.你想测试$ NF的内容为null,而不是NF的值为3。另外,任何命令都不要cmd file > file,因为shell可以在> file部分之前执行cmd file部分,因此在cmd读取之前删除输入文件

你需要:

awk -F', *' '$NF!=""' file > tmp && mv tmp file

这个问题/例子与自然语言处理完全无关,顺便说一句。

答案 4 :(得分:1)

这不是那么优雅,但可能更清晰,更容易修改字段编号:

#!/usr/bin/perl
open IN,$ARGV[0];
while(<IN>){
    @line = split(",",$_);
    if($line[2] =~ /\S/){
        print;
    }
}

$ ARGV [0]是您的表格的文件名称; \ S表示字段#2中的任何字符(非空白)(字段从0开始编号)。

答案 5 :(得分:0)

这是一个Perl答案,我有意选择演示-a autosplit和-F字段分隔符选项的用法:

perl -anF, -e 'print if $F[2] =~ /\S/' file > file.out

但在这种特殊情况下我可能更喜欢grep

grep -E -v ',\s*$' file > file.out