Spark - SELECT WHERE还是过滤?

lte*_*e__ 33 apache-spark apache-spark-sql

选择where子句和过滤Spark有什么区别?
是否存在一个比另一个更合适的用例?

我什么时候用

DataFrame newdf = df.select(df.col("*")).where(df.col("somecol").leq(10))
Run Code Online (Sandbox Code Playgroud)

什么时候

DataFrame newdf = df.select(df.col("*")).filter("somecol <= 10")
Run Code Online (Sandbox Code Playgroud)

更合适?

Yar*_*ron 66

根据spark文档 " where()是别名filter() "

filter(condition) 使用给定条件过滤行. where()是别名filter().

参数:条件-一个Columntypes.BooleanType或SQL表达式的字符串.

>>> df.filter(df.age > 3).collect()
[Row(age=5, name=u'Bob')]
>>> df.where(df.age == 2).collect()
[Row(age=2, name=u'Alice')]

>>> df.filter("age > 3").collect()
[Row(age=5, name=u'Bob')]
>>> df.where("age = 2").collect()
[Row(age=2, name=u'Alice')]
Run Code Online (Sandbox Code Playgroud)

  • 我知道已经有一段时间了,因为您已经回答了这个问题,但是使用Column或使用sql字符串进行过滤之间是否存在明显的性能差异? (2认同)
  • @Megan - 过滤时使用列或字符串之间没有显着的性能差异。它们都生成相同的物理计划,因此它们将以相同的方式执行。请参阅我的回答以了解更多详细信息。 (2认同)

Pow*_*ers 7

正如 Yaron 所提到的,where和之间没有任何区别filter

filter是采用列或字符串参数的重载方法。无论您使用何种语法,性能都是相同的。

过滤器重载方法

我们可以explain()看到所有不同的过滤语法生成相同的物理计划。假设您有一个包含person_nameperson_country列的数据集。以下所有代码片段将返回以下相同的物理计划:

df.where("person_country = 'Cuba'").explain()
df.where($"person_country" === "Cuba").explain()
df.where('person_country === "Cuba").explain()
df.filter("person_country = 'Cuba'").explain()
Run Code Online (Sandbox Code Playgroud)

这些都返回这个物理计划:

== Physical Plan ==
*(1) Project [person_name#152, person_country#153]
+- *(1) Filter (isnotnull(person_country#153) && (person_country#153 = Cuba))
   +- *(1) FileScan csv [person_name#152,person_country#153] Batched: false, Format: CSV, Location: InMemoryFileIndex[file:/Users/matthewpowers/Documents/code/my_apps/mungingdata/spark2/src/test/re..., PartitionFilters: [], PushedFilters: [IsNotNull(person_country), EqualTo(person_country,Cuba)], ReadSchema: struct<person_name:string,person_country:string>
Run Code Online (Sandbox Code Playgroud)

语法不会改变过滤器在后台执行的方式,但执行查询的文件格式/数据库会改变。Spark 将在 Postgres(支持谓词下推过滤)、Parquet(列修剪)和 CSV 文件上以不同的方式执行相同的查询。 请参阅此处了解更多详情。