Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/amazon-web-services/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Amazon web services 在spark MapTask中调用http请求和读取inputstream的有效方法是什么_Amazon Web Services_Apache Spark_Amazon S3_Java 7 - Fatal编程技术网

Amazon web services 在spark MapTask中调用http请求和读取inputstream的有效方法是什么

Amazon web services 在spark MapTask中调用http请求和读取inputstream的有效方法是什么,amazon-web-services,apache-spark,amazon-s3,java-7,Amazon Web Services,Apache Spark,Amazon S3,Java 7,请参阅下面的代码示例 JavaRDD<String> mapRDD = filteredRecords .map(new Function<String, String>() { @Override public String call(String url) throws Exception { BufferedReader in = nul

请参阅下面的代码示例

JavaRDD<String> mapRDD = filteredRecords
            .map(new Function<String, String>() {

                @Override
                public String call(String url) throws Exception {
                    BufferedReader in = null;
                    URL formatURL = new URL((url.replaceAll("\"", ""))
                            .trim());
                    try {
                        HttpURLConnection con = (HttpURLConnection) formatURL
                                .openConnection();
                        in = new BufferedReader(new InputStreamReader(con
                                .getInputStream()));

                        return in.readLine();
                    } finally {
                        if (in != null) {
                            in.close();
                        }
                    }
                }
            }); 
这段代码非常慢。IP和端口是随机的,负载是分布式的,所以IP可以有20个不同的端口值,所以我看不到瓶颈

当我评论

 in = new BufferedReader(new InputStreamReader(con
                            .getInputStream()));

                    return in.readLine();
代码太快了。 注:要处理的输入数据为10GB。使用spark从S3读取数据

BufferedReader或InputStreamReader有什么问题吗?还有其他选择吗。 我不能在spark中使用foreach,因为我必须从服务器获取响应,并且需要将JAVARdd保存为HDFS上的文本文件

如果我们使用mappartition代码,如下所示

JavaRDD<String> mapRDD = filteredRecords.mapPartitions(new FlatMapFunction<Iterator<String>, String>() {

        @Override
        public Iterable<String> call(Iterator<String> tuple) throws Exception {

            final List<String> rddList = new ArrayList<String>();
            Iterable<String> iterable = new Iterable<String>() {

                @Override
                public Iterator<String> iterator() {
                    return rddList.iterator();
                }
            };
            while(tuple.hasNext()) {
                URL formatURL = new URL((tuple.next().replaceAll("\"", ""))
                        .trim());
                HttpURLConnection con = (HttpURLConnection) formatURL
                        .openConnection();
                try(BufferedReader br = new BufferedReader(new InputStreamReader(con
                        .getInputStream()))) {

                    rddList.add(br.readLine());

                } catch (IOException ex) {
                    return rddList;
                }
            }
            return iterable;
        }
    }); 
JavaRDD mapRDD=filteredRecords.mapPartitions(新的FlatMapFunction(){
@凌驾
公共Iterable调用(迭代器元组)引发异常{
最终列表rddList=newarraylist();
Iterable Iterable=新的Iterable(){
@凌驾
公共迭代器迭代器(){
返回rddList.iterator();
}
};
while(tuple.hasNext()){
URL formatURL=新URL((tuple.next().replaceAll(\“”,“”))
.trim());
HttpURLConnection con=(HttpURLConnection)formatURL
.openConnection();
try(BufferedReader br=新的BufferedReader(新的InputStreamReader)(con
.getInputStream())){
添加(br.readLine());
}捕获(IOEX异常){
返回rddList;
}
}
返回可编辑;
}
}); 

这里还有我们正在做的每一条记录。不是吗?

您当前正在使用的

映射函数

它为分区中的每一行创建url请求

你可以用

地图分割


这将使代码运行得更快,因为它只创建到服务器的连接一次,即每个分区只有一个连接。

设置TCP/HTTPS连接是一个巨大的成本。这一事实加剧了这一点,即使您只读取第一个连接(短)一个大文件的行,为了更好地重复使用HTTP/1.1连接,现代HTTP客户机尝试将()读取到文件的末尾,以避免中断连接。这对于小文件是一个很好的策略,但对于MB大小的文件则不适用

这里有一个解决方案:在读取时设置内容长度,以便只读取较小的块,从而降低close()的成本;然后,连接循环可以降低HTTPS设置成本。这就是最新的Hadoop/Spark S3A客户端在连接上设置fadvise=random时所做的:请求块,而不是整个多GB文件。请注意:如果要逐字节地遍历一个文件,这种设计实际上非常糟糕

JavaRDD<String> mapRDD = filteredRecords.mapPartitions(new FlatMapFunction<Iterator<String>, String>() {

        @Override
        public Iterable<String> call(Iterator<String> tuple) throws Exception {

            final List<String> rddList = new ArrayList<String>();
            Iterable<String> iterable = new Iterable<String>() {

                @Override
                public Iterator<String> iterator() {
                    return rddList.iterator();
                }
            };
            while(tuple.hasNext()) {
                URL formatURL = new URL((tuple.next().replaceAll("\"", ""))
                        .trim());
                HttpURLConnection con = (HttpURLConnection) formatURL
                        .openConnection();
                try(BufferedReader br = new BufferedReader(new InputStreamReader(con
                        .getInputStream()))) {

                    rddList.add(br.readLine());

                } catch (IOException ex) {
                    return rddList;
                }
            }
            return iterable;
        }
    });