繁体   English   中英

'group by'适用于MySQL,但不适用于Oracle

[英]'group by' works on MySQL, but not Oracle

我有一个适用于MySQL的查询但不适用于Oracle,我正在尝试转换。 这是我的表:

unique_row_id  http_session_id  page_name   page_hit_timestamp
----------------------------------------------------------------
0              123456789        index.html  2010-01-20 15:00:00
1              123456789        info.html   2010-01-20 15:00:05
2              123456789        faq.html    2010-01-20 15:00:15
3              987654321        index.html  2010-01-20 16:00:00
4              987654321        faq.html    2010-01-20 16:00:05
5              987654321        info.html   2010-01-20 16:00:15
6              111111111        index.html  2010-01-20 16:01:00
7              111111111        faq.html    2010-01-20 16:01:05
8              111111111        info.html   2010-01-20 16:01:15

SQL是

select http_session_id, unique_row_id, page_name, page_hit_timestamp 
from page_hits 
group by http_session_id;

在MySQL上,这将返回3行(每个唯一的http_session_id一行)。

在Oracle上,我得到一个“ORA-00979:不是GROUP BY表达式”错误。 我也尝试过与众不同,但我无法让它发挥作用。

为了清楚 - 我想要一个ResultSet,每个唯一的http_session_id包含一行。 unique_row_id最好是最大值(例如http_session_id = 123456789为2),但这并不重要。

我快要把它分成多个单独的sql语句(一个“select distinct http_session_id”,另一个迭代所有这些并选择max(unique_row_id)。任何指针都会被感激地收到 - 我很想避免这个!

Rgds,凯文。

您遇到ORA错误的原因是因为MySQL支持非标准GROUP BY子句,称其为“功能”。 在这里记录

标准SQL GROUP BY子句必须包含SELECT子句中指定的所有列,这些列不包含在GROUP BY子句中指定的聚合函数(LIKE COUNT,MAX / MIN等)中。

如果你想为每个http_session_id值设置一个唯一行 - 请查看使用ROW_NUMBER:

SELECT x.*
  FROM (select http_session_id, unique_row_id, page_name, page_hit_timestamp,
               ROW_NUMBER() OVER (PARTITION BY http_session_id 
                                      ORDER BY http_session_id) AS rank
          FROM page_hits) x
 WHERE x.rank = 1

这会工作:

select max(unique_row_id), http_session_id
from page_hits
group by http_session_id

顺便说一下 ; 我的sql在结果集中返回的结果集中返回的columsn是什么,而不是group by子句? (page_name,page_hit_timestamp)

我认为GROUP BY需要在SQL标准的WHERE子句或聚合函数中使用变量吗?

尝试使用SELECT MAX(unique_row_id) GROUP BY http_session_id

在标准SQL中,如果您有GROUP BY子句,则不属于它的所有列都必须在聚合中。 在MySQL中,这个规则在设计上放松了。

例如,这在MySQL中是允许的,但在标准SQL中则不允许:

SELECT customer_id, country, SUM(amount) FROM records GROUP BY customer_id

有一点需要注意:MySQL假设您知道自己在做什么。 如果同一个客户在多个国家/地区都有记录,则查询将只是抓取表中的第一个国家/地区,而忽略所有其他国家/地区。 此外,由于行的顺序未定义,并且没有ORDER BY,因此每次运行查询时可能会得到不同的结果。

在标准SQL中,您有两种选择:

SELECT customer_id, country, SUM(amount) FROM records GROUP BY customer_id, country

要么

SELECT customer_id, MIN(country), SUM(amount) FROM records GROUP BY customer_id

Oracle中的另一个选项,如果您需要:

select DISTINCT
       FIRST_VALUE(unique_row_id)
       OVER (PARTITION BY http_session_id
             ORDER BY unique_row_id DESC) unique_row_id,
       http_session_id,
       FIRST_VALUE(page_name)
       OVER (PARTITION BY http_session_id
             ORDER BY unique_row_id DESC) page_name,
       FIRST_VALUE(page_hit_timestamp)
       OVER (PARTITION BY http_session_id
             ORDER BY unique_row_id DESC) page_hit_timestamp
from page_hits;

这将让一组不同的http_session_id的,并为每个返回的unique_row_idpage_namepage_hit_timestamp从具有最大的行unique_row_idhttp_session_id ,如:

unique_row_id  http_session_id  page_name   page_hit_timestamp
----------------------------------------------------------------
2              123456789        faq.html    2010-01-20 15:00:15
5              987654321        info.html   2010-01-20 16:00:15
8              111111111        info.html   2010-01-20 16:01:15

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM