我们应该为SparkSQL中的连接查询中的每个表创建单独的数据帧

时间:2018-01-29 12:10:18

标签: apache-spark apache-spark-sql

我们需要在Spark SQL中转换并执行执行配置单元查询。查询涉及2个表之间的连接。我们将创建一个数据帧,然后在其上创建sparksql查询。请找到样本配置单元查询以及转换后的查询。 / p>

------ Hive查询

select a.col1,a.col2,a.col3,b.col4,b.col5,b.col6.b.col7
from table1 a left outer join table2 b
on a.col3=b.col3

----- Spark SQL

import org.apache.spark.sql.hive.HiveContext
val hiveContext = new org.apache.spark.sql.hive.HiveContext(sc)
val q1=hivecontext.sql("select col1,col2,col3,col4 from table1");
val q2=hivecontext.sql("select col3,col5,col6,col7 from table2");
val q3=q1.join(q2,q1("col3")===q2("col3"));

但我们也可以在单个数据框中执行整个查询,如下所示

**

val q5=hivecontext.sql("select 
a.col1,a.col2,a.col3,b.col4,b.col5,b.col6.b.col7
from table1 a left outer join table2 b
on a.col3=b.col3")**

我想知道在这种情况下我们最好使用哪种方法(单一与多种数据帧),以及在各种参数(如性能和可读性)方面优于其他方法。

2 个答案:

答案 0 :(得分:0)

第二种方法似乎在所有方面都是明智的

  1. 当您在Hive数据上运行SQL时,HiveContext将在hive中运行查询并将结果元数据返回给Spark。所以spark只需要存储生成的元数据集。但在上面的例子中,它必须将hive中的所有数据存储到其RDD中。
  2. 维护单个RDD也有助于优化DAG。
  3. 如果您作为单个查询运行,即使Spark催化剂也会对其进行更优化。
  4. 可读性看起来更好。

答案 1 :(得分:0)

两种方法都是相同的。从性能的角度来看,它并不重要。 Catalyst优化器将为这两个查询创建相同的物理计划。

现在还有其他方面需要考虑。编写SQL查询通常很容易,但是您放松了编译时类型检查。如果SQL中有拼写错误或列名不正确,则除非在群集上运行,否则无法找到。但是,如果您使用的是数据帧操作,则代码将无法编译。因此它有助于加快编码速度。

但是,再次使用数据帧API编写复杂的SQL并非易事。因此,通常我使用Dataframe API,其中操作相对容易,并使用SQL进行复杂查询。