SPARK UDF多次执行的问题

SPARK UDF多次执行的问题


通常我们在一个dataframe中调用udf时,我们预期是每一行应用一次udf函数,但实际上这是不能保证每一行应用一次的,因为在一些可能多次访问udf返回值得场景下,spark内部会优先反复调用udf而不是job。
所以我们在设计udf时应该设计为pure function,这样可以保证即使对于同一条数据多次调用udf也不会影响预期结果,否则应该考虑使用map/mapPartitions实现你的需求
下方引用spark jira上的问题描述

Spark assumes UDF’s are pure function; we do not guarantee that a function is only executed once. This is due to the way the optimizer works, and the fact that sometimes retry stages. We could add a flag to UDF to prevent this from working, but this would be a considerable engineering effort.
The example you give is not really a pure function, as its side effects makes the thread stop (changes state).
If you are connecting to an external service, then I would suggest using Dataset.mapPartitions(…) (similar to a generator). This will allow you to setup one connection per partition, and you can call a method as much or as little as you like.

jira链接:UDFs are run too many times

Apache Spark 是一个不断发展和演化的开源项目,其版本发布和变体选择非常丰富,涵盖了不同的用途、平台适配以及性能优化。以下是关于 Apache Spark 的主要变体和版本信息的详细说明。 ### ### Apache Spark 主要版本演变 Apache Spark 的版本号遵循语义化版本控制(Semantic Versioning),通常以 `x.y.z` 的形式表示,其中 `x` 表示主版本,`y` 表示次版本,`z` 表示修订版本。以下是其主要版本的演进: - **Spark 1.x**:这是 Spark 的早期版本,引入了核心的 RDD(弹性分布式数据集)编程模型,支持批处理和交互式查询。Spark 1.6 是该系列的最后一个稳定版本,于 2016 年发布[^1]。 - **Spark 2.x**:这一系列版本引入了结构化数据处理的核心抽象——DataFrame 和 Dataset,同时增强了 SQL 查询能力、Tungsten 引擎和 Catalyst 优化器。Spark 2.4 是该系列的最后一个版本,支持许多流处理改进和结构化流(Structured Streaming)功能[^2]。 - **Spark 3.x**:该系列版本专注于性能优化、扩展性和易用性提升。主要特性包括自适应查询执行(Adaptive Query Execution)、动态分区合并(Dynamic Partition Pruning)、向量化 UDF 支持等。Spark 3.3 是当前较为稳定的版本之一,进一步增强了与云平台的集成能力[^3]。 - **Spark 4.x(开发中)**:Spark 4.0 尚未正式发布,但社区已经在讨论其潜在的改进方向,包括更深层次的流批一体优化、更好的资源管理支持(如与 Kubernetes 的集成)等。 ### ### Apache Spark 的主要变体 Apache Spark 除了官方发布的主版本外,还存在多个基于其核心进行定制或优化的变体,适用于特定场景或平台: - **Databricks Runtime**:由 Databricks 提供,是基于 Spark 的增强版本,集成了 Delta Lake、MLflow、优化后的查询引擎等工具,适用于大规模数据湖和机器学习工作负载。 - **Spark on Kubernetes**:这是一种部署变体,允许 Spark 应用程序直接运行在 Kubernetes 集群上,提供更好的云原生支持和资源隔离能力。 - **Spark with Delta Lake**:Delta Lake 是一个开源存储层,提供 ACID 事务、时间旅行(time travel)、模式演化(schema evolution)等功能,可与 Spark 无缝集成,适用于需要高可靠性和版本控制的数据湖场景。 - **Spark Thrift Server**:为 Spark 提供了 JDBC/ODBC 接口,允许用户通过 SQL 客户端工具(如 BI 工具)访问 Spark 集群,适用于构建数据仓库和报表系统。 - **Spark NLP**:由 John Snow Labs 维护,是 Spark 的自然语言处理扩展库,集成了大量预训练模型和深度学习功能,适用于文本分析和 AI 应用场景。 - **GraphX 和 GraphFrames**:GraphX 是 Spark 的图计算库,支持图算法和图结构操作;GraphFrames 是其 DataFrame 风格的扩展,支持更灵活的图查询和分析。 ### ### Spark 的部署模式与执行引擎 - **Standalone 模式**:Spark 自带的简单集群管理器,适用于小型部署或测试环境。 - **YARN 模式**:在 Hadoop 集群中运行 Spark,利用 YARN 进行资源调度,适用于已有的 Hadoop 生态系统。 - **Mesos 模式**:使用 Apache Mesos 作为资源调度器,适用于多租户和混合工作负载场景。 - **Kubernetes 模式**:在 Kubernetes 上运行 Spark,支持动态资源分配和容器化部署,适用于现代云原生架构。 ### ### Spark执行引擎优化 - **Tungsten 引擎**:用于 Spark 2.x 的二进制存储和代码生成技术,显著提升了 CPU 和内存效率。 - **Adaptive Query Execution (AQE)**:在 Spark 3.0 引入,支持运行时动态优化物理执行计划,如合并分区、调整连接策略等,从而提高查询性能。 - **Dynamic Partition Pruning**:在 Spark 3.0 中增强,允许在运行时根据实际数据分布剪枝不必要的分区,减少 I/O 和计算资源消耗。 ### ### 示例:Spark 3.3 的主要特性 ```scala // 示例:使用 Spark 3.3 的 AQE 功能 spark.conf.set("spark.sql.adaptive.enabled", "true") spark.conf.set("spark.sql.adaptive.skewedJoin.enabled", "true") val df = spark.read.parquet("path/to/data") df.createOrReplaceTempView("data") val result = spark.sql("SELECT * FROM data WHERE id > 1000") result.show() ``` ###
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值