所以我有一个奇怪的情况,其中两个非常相似的查询返回不同的结果。第一个查询是这样的:
select src.period_num period_num,
src.flag flag,
src.week_num week_num,
((src.year_num * 100) + src.period_num) year_num,
count(distinct src.id) result_count
from src_table src
group by src.period_num,
src.flag,
src.week_num,
((src.year_num * 100) + src.period_num)
第二个查询是这个查询:
select src.period_num period_num,
src.flag flag,
src.week_num week_num,
((src.year_num * 100) | src.period_num) year_num,
count(distinct src.id) result_count
from src_table src
group by src.period_num,
src.flag,
src.week_num,
((src.year_num * 100) | src.period_num)
如您所见,查询只有一个区别-在第一个查询中,我们使用加法(+),在第二个查询中,我们使用按位OR(|) 我的问题是,对于第一个结果,我们会收到类似的结果(我只留下了大部分):
+-------------+---------+-----------+-----------+---------------+--+
| period_num | flag | week_num | year_num | result_count |
+-------------+---------+-----------+-----------+---------------+--+
| 6 | true | 21 | 201906 | 94 |
而第二个返回此:
+-------------+---------+-----------+-----------+---------------+--+
| period_num | flag | week_num | year_num | result_count |
+-------------+---------+-----------+-----------+---------------+--+
| 6 | true | 21 | 201902 | 87 |
| 6 | false | 21 | 201902 | 7 |
第二个结果计数是正确的,带有正确的按标志分组,但是您可以看到现在year_num变得混乱了。无论如何,我的主要问题是我无法理解第一个查询到底出了什么问题,因为它似乎并没有带来什么问题。 任何想法和帮助,表示赞赏。
答案 0 :(得分:0)
按位或与加法完全不同的操作。因此,它将产生完全不同的结果。
请考虑以下两个二进制“操作”示例。
第一次加法(1 + 3 = 4):
0001
+ 0011
----
= 0100
和按位或(1 | 3 = 3):
0001
+ 0011
----
= 0011
我希望这可以帮助您解决问题。
哦,请记住,将数字乘以100会在基数10(十进制)中引入两个尾随零,但是在二进制中,最低有效位上仍可能设置位。
例如,201900以二进制形式110001010010101100
。
在没有更多细节的情况下,很难解释为什么简单地通过按位或加法将src.flag神奇地从false更改为true。准备您的示例,是否有可能不小心更改了其他内容?
按照承诺,我已经通过Spark-SQL运行您的示例数据。我将您的数据集减少为仅94条记录,其中year_num = 2019和period_num = 6。
这是运行的结果,显示为两个查询生成相同的答案。接下来就是整个过程,如果您可以使用spark-shell,可以尝试一下。蜂巢中可能有一个错误,但我不会从这个假设开始。
scala> val sumDF=sql("""select src.period_num period_num,
| src.flag flag,
| src.week_num week_num,
| ((src.year_num * 100) + src.period_num) year_num,
| count(distinct src.id) result_count
| from src_table src
| group by src.period_num,
| src.flag,
| src.week_num,
| ((src.year_num * 100) + src.period_num)
| """)
sumDF: org.apache.spark.sql.DataFrame = [period_num: int, flag: boolean ... 3 more fields]
scala> sumDF.show
+----------+-----+--------+--------+------------+
|period_num| flag|week_num|year_num|result_count|
+----------+-----+--------+--------+------------+
| 6|false| 21| 201906| 7|
| 6| true| 21| 201906| 87|
+----------+-----+--------+--------+------------+
scala> val orDF=sql ("""select src.period_num period_num,
| src.flag flag,
| src.week_num week_num,
| ((src.year_num * 100) | src.period_num) year_num,
| count(distinct src.id) result_count
| from src_table src
| group by src.period_num,
| src.flag,
| src.week_num,
| ((src.year_num * 100) | src.period_num)
| """)
orDF: org.apache.spark.sql.DataFrame = [period_num: int, flag: boolean ... 3 more fields]
scala> orDF.show
+----------+-----+--------+--------+------------+
|period_num| flag|week_num|year_num|result_count|
+----------+-----+--------+--------+------------+
| 6| true| 21| 201902| 87|
| 6|false| 21| 201902| 7|
+----------+-----+--------+--------+------------+
这是完整的工作:
var dataDF=spark.read.option("header","true").option("inferSchema","true").csv("source_data_from_op_2019_06.csv")
dataDF.printSchema
dataDF.count
dataDF.show
dataDF.createOrReplaceTempView("src_table")
val sumDF=sql("""select src.period_num period_num,
src.flag flag,
src.week_num week_num,
((src.year_num * 100) + src.period_num) year_num,
count(distinct src.id) result_count
from src_table src
group by src.period_num,
src.flag,
src.week_num,
((src.year_num * 100) + src.period_num)
""")
sumDF.show
val orDF=sql ("""select src.period_num period_num,
src.flag flag,
src.week_num week_num,
((src.year_num * 100) | src.period_num) year_num,
count(distinct src.id) result_count
from src_table src
group by src.period_num,
src.flag,
src.week_num,
((src.year_num * 100) | src.period_num)
""")
orDF.show
您可以在Spark-shell中尝试吗?