为什么在SQL查询中使用UDF会导致笛卡尔积?

Sah*_*een 1 sql apache-spark apache-spark-sql

我看到了Databricks-Question并且不明白

  1. 为什么使用UDF导致笛卡尔积而不是完全外连接?显然,笛卡尔积将比完整外连接(联接是一个例子)更多行,这是潜在的性能损失.
  2. Databricks-Question中给出的示例中,是否有任何强制外部连接超过笛卡尔积的方法?

在这里引用Databricks-Question:

我有一个Spark Streaming应用程序,它使用SQLContext在流数据上执行SQL语句.当我在Scala中注册自定义UDF时,流应用程序的性能显着下降.详情如下:

声明1:

Select col1, col2 from table1 as t1 join table2 as t2 on t1.foo = t2.bar

声明2:

Select col1, col2 from table1 as t1 join table2 as t2 on equals(t1.foo,t2.bar)

我使用SQLContext注册自定义UDF,如下所示:

sqlc.udf.register("equals", (s1: String, s2:String) => s1 == s2)

在相同的输入和Spark配置上,与Statement1相比,Statement2的性能明显更差(接近100倍).

zer*_*323 7

为什么使用UDF导致笛卡尔积而不是完全外连接?

使用UDF需要笛卡尔积的原因非常简单.由于您传递具有可能无限域和非确定性行为的任意函数,因此确定其值的唯一方法是传递参数并进行求值.这意味着您只需检查所有可能的对.

另一方面,简单的平等具有可预测的行为.如果你使用t1.foo = t2.bar的条件,你可以简单地洗牌t1,并t2通过行foobar分别获得预期的结果.

而在关系代数中准确地说,外连接实际上是使用自然连接表示的.除此之外的任何事情都只是一种优化.

任何强制外部连接超过笛卡尔积的方法

不是,除非你想修改Spark SQL引擎.