Spark与缓存

预期成果

1.1   当前问题

当前以图搜图应用存在的问题:

  1. 当前使用spark RDD方案无法达到数据实时加载(每10分钟加载一次,虽然可配,但太短可能会有问题)
  2. Spark RDD内存会被分为两部分,一部分用来缓存数据一部分用来计算,Spark默认配置只有差不多50%的内存用于缓存(也就是说executor配了100G,只有50多G可以被用来做缓存),虽然比例可以进行配置,但增加缓存内存比例后,是否会影响计算性能有待测试。
  3. 当前数据全缓存到spark jvm内存中,GC时间较长会导致影响计算性能
  4. 当前加载的RDD只有自身context才能使用,无法做到应用间共享
  5. 当driver端服务宕掉后,缓存的数据也会丢失
  6. 期望能将增量数据加载时间缩小到足够小达到准实时,或者直接能够达到实时
  7. 职责分明,缓存有分布式缓存做,Spark只负责计算
  8. 缓存数据不占用Spark jvm内存,减少GC对计算的影响
  9. 加载到内存的数据可以被其他应用使用
  10. Driver端服务宕掉后,缓存数据不会丢失,其他driver段仍可使用
  11. 采用新方案对比原方案,性能损耗尽可能小,最好达到无损耗

1.2   预期成果

2       技术选型

根据上述问题和预期成果,期望选择一款与Spark结合较好的分布式内存缓存计算,从而将缓存工作从spark中抽离出来,让spark专注于计算。

2.1.1  Apache Ignite

Apache Ignite内存数据组织是高性能的、集成化的以及分布式的内存平台,他可以实时地在大数据集中执行事务和计算,和传统的基于磁盘或者闪存的技术相比,性能有数量级的提升。

选择预研该技术最大的原因为,Ignite实现了一个可共享的Spark RDD,可实现增量数据实时在比对中体现。

2.1.2  Alluxio(原Tachyon)

Alluxio在1.0版本后由原来的Tcahyon更名。Alluxio与Spark结合较好,Spark1.5后增加的缓存方式:OFF_HEAP(堆外缓存)当前只支持tachyon。

不过Alluxio和Spark RDD一样都不可变,缓存文件一旦写入就不能修改,且在完成写入之前缓存数据是无法读取的,这样就服务达到增量数据的实时性,但可以实现尽可能缩短增量加载时间来达到准实时性。

3       阶段性结论

性能测试采用上述两种技术三个版本(apache-ignite-fabric-1.5.0.final、alluxio-1.0.1、tachyon-0.7.1-hadoop2.6-build)八种方案:

  1. 直接采用Spark RDD缓存,且缓存数据不做序列化
  2. 直接采用Spark RDD缓存,缓存数据使用java序列化方式
  3. 直接采用Spark RDD缓存,缓存数据使用kryo序列化方式
  4. 采用Spark RDD OFF_HEAP模式(即缓存数据到tachyon),缓存数据使用java序列化方式
  5. 采用Spark RDD OFF_HEAP模式(即缓存数据到tachyon),缓存数据使用kryo序列化方式
  6. 使用tachyon缓存数据(调用saveAsObjectFile,直接将数据序列化成文件写到tachyon中),saveAsObjectFile使用java序列化方式
  7. 使用Alluxio缓存数据(调用saveAsObjectFile,直接将数据序列化成文件写到Alluxio中),saveAsObjectFile使用java序列化方式
  8. 使用ignite缓存数据,使用IgniteRDD进行统计

下面为三台256G内存集群,58727000条数据,Spark分配36核,测试结果如下:


缓存方式


内存配置


是否序列化


序列化实现


检索耗时(s)


内存空间(GB)


Spark RDD


executor:150GB*3



 


11.527


112.8


Spark RDD


executor:150GB*3



java


20.09


56.4


Spark RDD


executor:150GB*3



kryo


16.275


51.8


Spark RDD + tachyon


executor:20GB*3 tachyon:100GB*3



java


21.771


51.56


Spark RDD + tachyon


executor:20GB*3 tachyon:100GB*3



kryo


17.772


51.83


tachyon


executor:20GB*3 tachyon:100GB*3



java


32.719


53.03


Alluxio


executor:20GB*3 alluxio:100GB*3



java


26.988


53.03


ignite


executor:20GB*3 ignite:10GB*3(数据保存在堆外,不使用jvm内存)



java


333.228


 

由上表分析如下:

  1. 检索耗时最短为方案一,直接缓存到spark jvm中且不做序列化,但该方案占用内存也较多(目前是其他方案的两倍),不过当前以图搜图框架中数据结构采用map,所以较占内存
  2. 方案一、二、三对比,采用序列化会有性能损耗,kryo序列化耗时是java序列化的1/2,与之前测试基本一致,采用kryo序列化112GB数据耗时4-5秒
  3. 对比方案二、方案四以及方案三、方案五,从tachyon拉数据到spark进行计算耗时为1秒左右,但由于存储到tachyon必须序列化,所以得加上序列化的耗时,最少的性能损耗也差不多5-6秒
  4. 直接调用saveAsObjectFile保存数据到tachyon或者Alluxio,性能损耗较大,分别为22秒和14秒,初步估计性能损耗由于:(1)saveAsObjectFile采用java序列化方式,性能损耗将近9秒;(2)saveAsObjectFile内部实现使用的是hadoop api,tachyon能够兼容这些api,但可能有部分性能损耗;(3)spark可能对tachyon存储做过一定优化
  5. 由表格可以看出ignite结合spark性能很差,估计原因可能为:(1)可能修改某些配置后可以优化性能,但iginte资料非常少,特别是跟spark结合这块,基本没有什么资料;(2)ignite本身不单单包含存储功能,还有检索、计算等功能,所以它与spark本身也存在竞争关系

结论如下:

  1. ignite如需优化性能需要深入源码,且没有对比数据,具体最后能到什么程度无法预估,且当前基本没有什么已知公司使用该技术与Spark结合

Alluxio(Tachyon)性能优化需要看Spark缓存代码,但是该方法最终能够达到的性能指标基本能够预估(较现有方案有5-6秒的损耗,但内存消耗可能会有所减少)

时间: 2024-11-02 21:41:34

Spark与缓存的相关文章

Spark源码系列(五)RDD是如何被分布式缓存?

这一章想讲一下Spark的缓存是如何实现的.这个persist方法是在RDD里面的,所以我们直接打开RDD这个类. def persist(newLevel: StorageLevel): this.type = { // StorageLevel不能随意更改 if (storageLevel != StorageLevel.NONE && newLevel != storageLevel) { throw new UnsupportedOperationException("C

【Spark深入学习 -16】官网学习SparkSQL

----本节内容-------1.概览        1.1 Spark SQL        1.2 DatSets和DataFrame2.动手干活        2.1 契入点:SparkSession        2.2 创建DataFrames        2.3 非强类型结果集操作        2.4 程序化执行SQL查询        2.5 全局临时视图        2.6 创建DataSets        2.7 与RDD交互操作        2.8 聚集函数3.Sp

Spark调优

转载:http://www.oschina.net/translate/spark-tuning 因为大部分Spark程序都具有“内存计算”的天性,所以集群中的所有资源:CPU.网络带宽或者是内存都有可能成为Spark程序的瓶颈.通常情况下,如果数据完全加载到内存那么网络带宽就会成为瓶颈,但是你仍然需要对程序进行优化,例如采用序列化的方式保存RDD数据(Resilient Distributed Datasets),以便减少内存使用.该文章主要包含两个议题:数据序列化和内存优化,数据序列化不但能

Spark Job调优(Part 2)

原文链接:https://wongxingjun.github.io/2016/05/11/Spark-Job%E8%B0%83%E4%BC%98-Part-2/ 这篇文章将会完成Part 1中留下的部分,我会尽力介绍更多的你关心的能加速Spark程序的东西.特别是你将会学习资源调优或者配置Spark来充分利用集群提供的所有资源.然后我们会转向并行度调优,job性能中最难的也是最重要的参数.最后你会学习如何表示数据本身,Spark能读取的磁盘存储形式(用Apache Avro或者Apache P

Spark及其应用场景初探

最近老大让用Spark做一个ETL项目,搭建了一套只有三个结点Standalone模式的Spark集群做测试,基础数据量大概8000W左右.看了官方文档,Spark确实在Map-Reduce上提升了很多,可是官方明确提出了在Interactive Data 方面性能提升最大.但是做ETL的数据之间是平行结构,没有任何交互,数据处理完直接就推送走了,也不用做任何缓存,因此完全体现不出来Spark的优势.具体可以用下面这个例子来说, 假设Hadoop集群中有一个文件,每行有一个随机数,我们现在需要计

Apache Spark Jobs 性能调优

当你开始编写 Apache Spark 代码或者浏览公开的 API 的时候,你会遇到各种各样术语,比如transformation,action,RDD 等等. 了解到这些是编写 Spark 代码的基础. 同样,当你任务开始失败或者你需要透过web界面去了解自己的应用为何如此费时的时候,你需要去了解一些新的名词: job, stage, task.对于这些新术语的理解有助于编写良好 Spark 代码.这里的良好主要指更快的 Spark 程序.对于 Spark 底层的执行模型的了解对于写出效率更高

【转载】Apache Spark Jobs 性能调优(二)

调试资源分配   Spark 的用户邮件邮件列表中经常会出现 "我有一个500个节点的集群,为什么但是我的应用一次只有两个 task 在执行",鉴于 Spark 控制资源使用的参数的数量,这些问题不应该出现.但是在本章中,你将学会压榨出你集群的每一分资源.推荐的配置将根据不同的集群管理系统(YARN.Mesos.Spark Standalone)而有所不同,我们将主要集中在YARN 上,因为这个Cloudera 推荐的方式. Spark(以及YARN) 需要关心的两项主要的资源是 CP

spark性能调优(四) spark shuffle中JVM内存使用及配置内幕详情

转载:http://www.cnblogs.com/jcchoiling/p/6494652.html 引言 Spark 从1.6.x 开始对 JVM 的内存使用作出了一种全新的改变,Spark 1.6.x 以前是基于静态固定的JVM内存使用架构和运行机制,如果你不知道 Spark 到底对 JVM 是怎么使用,你怎么可以很有信心地或者是完全确定地掌握和控制数据的缓存空间呢,所以掌握Spark对JVM的内存使用内幕是至关重要的.很多人对 Spark 的印象是:它是基于内存的,而且可以缓存一大堆数据

Spark零基础学习笔记(一)——Python版

由于Scala才刚刚开始学习,还是对python更为熟悉,因此在这记录一下自己的学习过程,主要内容来自于spark的官方帮助文档,这一节的地址为: http://spark.apache.org/docs/latest/quick-start.html 文章主要是翻译了文档的内容,但也在里边加入了一些自己在实际操作中遇到的问题及解决的方案,和一些补充的小知识,一起学习. 环境:Ubuntu 16.04 LTS,Spark 2.0.1, Hadoop 2.7.3, Python 3.5.2, 利用