Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/apache-spark/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Apache spark 使用LIMIT对Spark SQL查询进行两次求值时获得相同的结果_Apache Spark_Pyspark_Apache Spark Sql_Pyspark Sql - Fatal编程技术网

Apache spark 使用LIMIT对Spark SQL查询进行两次求值时获得相同的结果

Apache spark 使用LIMIT对Spark SQL查询进行两次求值时获得相同的结果,apache-spark,pyspark,apache-spark-sql,pyspark-sql,Apache Spark,Pyspark,Apache Spark Sql,Pyspark Sql,我最近开始使用pyspark,我遇到了一些我试图更好地理解和避免的行为 考虑以下代码: query1 = "SELECT * FROM A where X >= 1000000 and X < 1001000 LIMIT 50" s1 = spark.sql(query1) X_vals = s1.select('X').rdd.flatMap(lambda x: x).collect() query2 = "SELECT * FROM B" + " where Y in " +

我最近开始使用pyspark,我遇到了一些我试图更好地理解和避免的行为

考虑以下代码:

query1 = "SELECT * FROM A where X >= 1000000 and X < 1001000 LIMIT 50"
s1 = spark.sql(query1)
X_vals = s1.select('X').rdd.flatMap(lambda x: x).collect()

query2 = "SELECT * FROM B" + " where Y in " + '('  + ','.join([str(x) for x in X_vals]) + ')'
s2 = spark.sql(query2)

s1.write.mode('overwrite').option("header", True).option("sep",'\t').csv('test/A.csv')
s2.write.mode('overwrite').option("header", True).option("sep",'\t').csv('test/B.csv')
query1=“从X>=1000000和X<1001000限制50的列表中选择*”
s1=spark.sql(查询1)
X_vals=s1.select('X').rdd.flatMap(lambda X:X).collect()
query2=“从B“+”中选择*,其中Y位于“+”(“+”,“.join([str(x)表示x中的x])+”)
s2=spark.sql(查询2)
s1.write.mode('overwrite')。option('header',True)。option('sep','\t')。csv('test/A.csv'))
s2.write.mode('overwrite')。option('header',True)。option('sep','\t')。csv('test/B.csv'))
A
中,我从一个范围中获取了50条记录的样本,并将
X
的值存储在
X\u vals
中。然后,我从表
B
中获取相同的记录(其中
Y
X\u vals
中)

稍后,我将这两个表写入
csv
文件。在生成的
csv
文件中,
A
中的
X
B
中的
Y
不再匹配

我认为这是可以解释的行为,是由懒惰的评估造成的;在
collect()
语句中选择的记录与
.csv
语句中选择的记录不同。然而,我对Spark的理解还不足以确切解释为什么会发生这种情况

所以,;为什么会发生这种情况,有没有办法强制查询返回相同的结果两次(而不加入表)

谢谢


Florian

问题在于实施
限制
。它是通过将记录洗牌到单个分区来实现的(您可以在的优秀答案中找到详细的解释)

同时,Spark遵循SQL标准规则——如果没有明确的顺序,那么优化器可以选择任意记录

val df = spark.range(1000)

df.where($"id".between(100, 200)).limit(10).explain
== Physical Plan ==
CollectLimit 10
+- *LocalLimit 10
   +- *Filter ((id#16L >= 100) && (id#16L <= 200))
      +- *Range (0, 1000, step=1, splits=4)

使用
orderby
将query1强制为特定的订单怎么样?@Bala,我想
orderby确实可以
工作,尽管我不确定。我对这种行为的直观解释是,上述行为是随机的,因为它取决于哪个执行者首先完成。在按订购的情况下,它会先收集20条记录,然后再订购,还是先订购所有记录,然后再收集?
df.where($"id".between(100, 200)).orderBy("id").limit(10).explain
== Physical Plan ==
TakeOrderedAndProject(limit=10, orderBy=[id#16L ASC NULLS FIRST], output=[id#16L])
+- *Filter ((id#16L >= 100) && (id#16L <= 200))
   +- *Range (0, 1000, step=1, splits=4)