scala - SPARK:尽管有缓存,但仍生成相同的阶段
问题描述
我想知道我怎么能有两个完全相同的阶段,尽管我在 Spark 中的每个操作之前缓存了我的数据。你能看看下面的截图吗,我觉得它很奇怪。这是否意味着我分阶段执行任务两次?
不幸的是,很难给出代码示例,但我会尝试解释我的工作。
- 从 CSV 读取数据
- 对特定列进行一些转换。
- 应用架构 ->
spark.Session.createDataFrame(df.rdd,schema)
- 通过在第 3 点创建的 DF 上使用不同的过滤器创建 7 个新数据帧)
- 出于比较的原因,从第 4 点获取两个数据帧并将它们传递给另一种方法。
我在第 2 点之后和第 4 点之后坚持只将要比较的两个数据帧。并在比较后不坚持。比较是一个漫长而复杂的过程。
解决方案
您可以使用 explain 运算符查看 DataFrame 是否缓存在您的物理计划中(其中 InMemoryRelation 实体反映缓存的数据集及其存储级别):
== Physical Plan ==
*Project [id#0L, id#0L AS newId#16L]
+- InMemoryTableScan [id#0L]
+- InMemoryRelation [id#0L], true, 10000, StorageLevel(disk, memory, deserialized, 1 replicas)
+- *Range (0, 1, step=1, splits=Some(8))
在你缓存(或持久化)你的 DataFrame 之后,第一个查询可能会变慢,但它会为以下查询带来回报。
您可以使用以下代码检查数据集是否已缓存:
scala> :type q2
org.apache.spark.sql.Dataset[org.apache.spark.sql.Row]
val cache = spark.sharedState.cacheManager
scala> cache.lookupCachedData(q2.queryExecution.logical).isDefined
res0: Boolean = false
Spark SQL 中的缓存有一个惊喜。缓存是惰性的,这就是为什么你要付出额外的代价来缓存第一个动作的行,但这只会发生在 DataFrame API 上。在 SQL 中,缓存是急切的,这会对查询性能产生巨大影响,因为您无需调用操作来触发缓存。
推荐阅读
- database - Rust 返回 leveldb 数据库实例
- python - 当我们有多个目标时,sklearn 中 LASSO 的目标函数是什么?
- tensorflow - Tensorflow Federated 中的联邦学习,有没有办法在客户端应用早期停止?
- c# - 如何在运行时编译 C# 代码目标 .NET 5?
- c++ - boost::system::error_code 和 boost::system::error_code::value() 有什么区别?
- python - 如何向数据框添加列并将所有行设置为特定值
- reactjs - 如何在 React SSR 中为可加载组件制作占位符
- sql - 在哪里存储 Rest API
- html - 如何让正确的元素溢出?
- java - 为什么在重启应用程序时为 Object 生成相同的哈希码?