使用Bash脚本查找包含特定数字范围的文件名

时间:2015-03-03 22:08:20

标签: xml linux bash shell grep

我有一堆.NFO文件,其中包含有关电影的元数据(基本上是XML格式)。我想创建一个循环遍历所有.NFO文件的bash脚本,并列出包含等于或小于5.0的评级的文件名。评级位于XML标记<rating>number</rating>

我能够使用grep在文本文件中查找特定单词并且它适用于:

grep "rating" . -R

结果为movie_name.nfo: <rating>7.5</rating>

我尝试了以下但是没有用:

grep "<rating>[0.0-9.0]</rating>" . -R

提前致谢

3 个答案:

答案 0 :(得分:2)

使用GNU grep:

grep -oP '<rating>\K(5\.0|[0-4]\.[0-9])(?=<)'

输出(例如)

4.3

答案 1 :(得分:1)

试试这个gnu grep解决方案:

echo "movie_name.nfo: <rating>4.5</rating>" | grep -Eo "[0-4]\.[[:digit:]]+|5\.0"
4.5

这里我们使用扩展正则表达式来匹配小于或等于5.0的任何值,方法是匹配5.0或0到4之间的任何数字,然后是文字点,然后是一个或多个数字出现(0-9)。

根据您的评论,您可以尝试以下sed解决方案,以确保不会选择不需要的值:

sed -nr 's/.*<rating>([0-4]\.[[:digit:]]+|5\.0).*/\1/p' file.txt

答案 2 :(得分:0)

我建议使用xml解析器,例如XML::Twig语言的perl。它是一个简单的程序,并且依赖于您正在使用的shell,可以使用正则表达式语法调用它以在同一命令中传递许多文件。代码很简单:

#!/usr/bin/env perl

use strict;
use warnings;
use XML::Twig;

for my $f (@ARGV) {
    XML::Twig->new(
        twig_handlers => {
            'rating' => sub {
                printf qq|%s\n|, $f if $_->text_only && $_->text_only < 5;
            },  
        },  
    )->parsefile($f);
}

并称之为:

perl script.pl xmlfile*

它将输出包含任何<rating>元素且值小于5的每个文件的名称。