有没有办法过滤包含特定模式的RDD

时间:2016-03-03 16:06:26

标签: java apache-spark

在下面的代码中,我正在过滤包含404 HTTP状态代码的日志,但现在我想要过滤包含400-405任何HTTP状态代码的日志。

JavaRDD<String> IPList = sc.textFile("/home/bhaumik/Documents/access_log", 1)
        .filter(new Function<String, Boolean>() {

            @Override
            public Boolean call(String v1) throws Exception {
                // TODO Auto-generated method stub
                return v1.contains(" 404 ");
            }
        });

那么有没有选择呢?

鉴于我的样本日志记录

64.242.88.10 - - [07/Mar/2004:20:55:43 -0800] "GET /mailman/listinfo/hs_support HTTP/1.1" 200 6294
64.242.88.10 - - [07/Mar/2004:20:56:56 -0800] "GET /twiki/bin/view/TWiki/WebTopicList HTTP/1.1" 200 14070
64.242.88.10 - - [07/Mar/2004:20:58:27 -0800] "GET /twiki/bin/attach/TWiki/WebPreferences HTTP/1.1" 401 12846
64.242.88.10 - - [07/Mar/2004:21:03:48 -0800] "GET /twiki/bin/view/TWiki/TWikiFAQ HTTP/1.1" 200 12050
64.242.88.10 - - [07/Mar/2004:21:06:05 -0800] "GET /twiki/bin/oops/TWiki/DefaultPlugin?template=oopsmore&param1=1.5&param2=1.5 HTTP/1.1" 200 11281

2 个答案:

答案 0 :(得分:2)

我认为正则表达式适用于此:

return v1.matches(".*40[0-5].*")

这匹配任何包含400-405的字符串。这也意味着如果400以另一种方式进入日志,它将会获取它。您可能希望拆分分隔符,然后转换为Int并进行适当的检查。

答案 1 :(得分:2)

一种简单的方法是:

return v1.contains(" 400 ")||v1.contains(" 401 ")||v1.contains(" 402 ");

但是当文件大小为400 ... 405

时,你可能会得到误报

一种替代方案可能是:

String[] parts = v1.split(" ");
return parts[parts.length - 2].matches("40[0-5]");

希望它有所帮助。