【问题标题】:Spark performance analysis for joins连接的 Spark 性能分析
【发布时间】:2015-10-29 05:42:43
【问题描述】:

输入数据

我有两个从 MySQL 导出为 csv 文件的表。

磁盘上的表 1 大小:250 MB 记录:70 万

磁盘上的表 2 大小:350 MB 记录:60 万

代码更新

import org.apache.spark.sql.SQLContext
val sqlContext = new SQLContext(sc)
val table-one = sqlContext.read.format("com.databricks.spark.csv").option("header", "true").load("example-input-files/table-1-data.csv”)
table-one.registerTempTable(“table-one”)
val table-two = sqlContext.read.format("com.databricks.spark.csv").option("header", "true").load("example-input-files/table-2-data.csv”)
table-two.registerTempTable(“table”-two)
sqlContext.cacheTable(“table-one”)
sqlContext.cacheTable(“table-two”)
val result = sqlContext.sql("SELECT table-one.ID,table-two.ID FROM table-one LEFT JOIN table-two ON table-one.ID = table-two.ID")
result.take(2).foreach(println)

Spark 工作

  • 使用Databricks CSV lib读取两个csv文件并将它们注册为 表格。

  • 使用公用列(典型的左列)对两者执行左连接 加入关系数据库发言。

  • 打印前两个结果,因为在控制台本身打印会 消耗时间。

这总共需要 30 秒。我在一台有足够内存的机器上运行,以便两个文件都可以容纳(毕竟它是 600Mb)。

我有两种方式来完成这项工作。

  • 整体运行作业,即加载所有 csv,运行连接,然后打印结果
  • 第二种方法是我第一次运行并使用sqlContext.cacheTable("the_table")在内存中缓存表

缓存后我发现join操作本身需要8秒才能完成。

这个时间合理吗?我猜它不是,可以做很多优化来加快查询速度。

我看到的优化

  • 将数据放入 HDFS 而不是本地磁盘。这会加快检索速度吗?
  • 在集群上运行,我猜这不会很快,因为数据可以放入内存并且顺序会更快。
  • 数据建模和使用 cassandra 会更快吗?
  • 我使用纯 SQL 加入,RDD 加入会更快吗?

还有其他方法可以做得更好吗?

【问题讨论】:

  • 当 Spark 旨在加速分布式计算时,使用少量数据和使用单个节点对 Spark 进行性能测试有点棘手。我认为你是对的,当你的数据有这种大小时,不值得去集群或 HDFS。你能把你的代码吗?
  • @mattinbits :我已经更新了代码。
  • 尝试在单个节点上优化代码不是一个好主意。尝试优化批处理集群计算引擎的 30 秒和 8 秒运行时间并不是一个好主意。尝试使用 Spark 处理 600MB 的数据并不是一个好主意。将数据转换为 Parquet 格式并进行压缩,这应该会提高性能。如果缓存有这么大的帮助,你会花很多时间在读取数据和反序列化数据上,Parquet 会改善这一点。我不会评论如何优化 Spark 的 8 秒运行时间
  • @0x0FFF :这正是我问这个问题的原因,我不知道从哪里开始。我只是在做一些实验,感谢您的建议,我会记住这一点。跨度>

标签: performance apache-spark bigdata distributed-computing apache-spark-sql


【解决方案1】:

正如评论者所说,Spark 专为分布式计算而设计。与其他 PL 相比,在本地处理小型(ish)数据时,仅所有初始化和调度的开销就足以让 Spark 看起来很慢。

在集群上运行,我猜这不会很快,因为 数据可以放入内存,顺序会更快。

只要您的代码执行狭窄的转换,执行程序实际上就会在内存中的本地数据副本上工作,因此这并不完全正确。但是,您的代码执行连接,这是一个广泛的转换 - 这意味着必须在网络中对块进行洗牌。请记住这一点。广泛的转换是昂贵的,因此尽可能将它们放在 DAG 的末尾。但同样,您的数据足够小,您可能看不到好处。

另一件事是,如果您有 Hive,那么您可以考虑将数据存储在按连接列分区的表中。

【讨论】:

    猜你喜欢
    • 2017-08-13
    • 1970-01-01
    • 2015-04-12
    • 2016-01-05
    • 1970-01-01
    • 1970-01-01
    • 2021-11-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多