【问题标题】:Select the lowest price by item in SQL with multiple joins在 SQL 中通过多个连接选择最低价格
【发布时间】:2017-10-05 09:07:09
【问题描述】:

我有多个代表航班数据的表格:

航班:

ID | NMB   | DATE
1  | CA1   | 2017-05-26
2  | CA1   | 2017-05-27
3  | CA2   | 2017-05-26
4  | CA2   | 2017-05-27

机场:

ID | NAME
1  | JFK
2  | LAX

航班到达:

ENTITY_ID (flights) | TARGET_ID (airports)
1                   | 1
2                   | 1
3                   | 2
4                   | 2

航班价格:

ENTITY_ID (flights) | VALUE
1                   | 455
2                   | 650
3                   | 750
4                   | 880

我正在尝试为每个到达机场的每个航班选择最低价格。我想要的是这个:

ID | ARRIVAL | PRICE
1  | 1       | 455
3  | 2       | 750

这是我构造的 SQL 查询,但在 flights_price 上应用的 MIN 函数不仅返回航班的最低价格,而且返回所有条目:

        SELECT
            f.id AS id,
            fa.target_id AS arrival,
            MIN(fp.value) AS price
        FROM flights_price AS fp
        JOIN flights AS f ON fp.entity_id=f.id
        JOIN flights_arrival AS fa ON fa.entity_id=f.id
        WHERE
          fa.target_id IN (1, 2)
        GROUP BY
          fa.target_id,
          fp.value,
          f.id;

我做错了什么?我也尝试了子查询,但没有成功。

【问题讨论】:

  • 作为一项规则,一组是由一个选择的东西组成的。如果这里对类似问题的十亿左右答案没有帮助,请参阅meta.stackoverflow.com/questions/333952/…
  • 这里的ARRIVAL列属于哪个表列
  • ARRIVAL 属于 flights_arrival,别名为 fa

标签: mysql sql join group-by min


【解决方案1】:

GROUP BY 中有 value 列,如果需要在其上应用聚合列,则需要将其从 GROUP BY 中删除(否则它将仅应用于每个组的一个值,使聚合冗余),例如:

SELECT fa.entity_id, f.name, fa.target_id, a.name, MIN(value)
FROM flights_arrival fa JOIN flights_price fp ON fa.entity_id = fp.flights
JOIN flights f ON fa.entity_id = f.id
JOIN airports a ON fa.target_id = a.id
WHERE fa.target_id IN (1,2)
GROUP BY fa.entity_id, f.name, fa.target_id, a.name;

【讨论】:

  • 如果我从 GROUP BY 中删除 fp.value 我得到错误:Syntax error or access violation: 1055 Expression #3 of ORDER BY clause is not in GROUP BY
【解决方案2】:

试试这个查询 -

SELECT fp.entity_id AS id, target_id AS arrival, MIN(value) AS price    
FROM flights_arrival AS fa
INNER JOIN flights_price AS fp ON (fp.entity_id = fa.entity_id)
GROUP BY target_id;

根据您的输出和尝试过的查询,我猜您只需要有到达和价格的航班。这就是为什么不需要使用航班表的原因。您还可以在 group by 之前添加 WHERE 过滤器,以获取特定 id 而不是所有航班的结果。

entity_id 列可能在 SELECT 语句中,即使它不在 GROUP BY 中,因为 db 是 MySQL。此外,在 flights_price 表中,entity_id 是唯一的,因此 fp.entity_id 将获得最低价格的正确值。

SQLfiddle

【讨论】:

  • 您建议的查询不起作用。每当您在请求中的选定字段上GROUP BY 时,您必须在其他选定字段上使用GROUP BY。否则,SQL 将抛出 Syntax error of ORDER BY clause 异常。在这种情况下,我们必须在fp.valuefp.entity_id 字段上有一个GROUP BY 表达式。但是你说我根本不需要飞行表,这是真的,我继续测试没有它的请求。
  • 您使用的是 MySQL 对吗? MySQL (5.9) 允许选择不在 group by 语句中的列。请参阅此fiddle。如果您不使用 MySQL,则查询将不起作用。
  • 是的,我正在使用 MySQL (5.7.17),但查询不起作用,我收到 GROUP BY 异常,也许我做错了什么。你的小提琴有效,谢谢你把它放在那里。我会继续努力的。
  • 告诉我进展如何。我也很想知道您为什么会遇到该异常。
猜你喜欢
  • 2018-03-16
  • 2019-02-15
  • 1970-01-01
  • 2013-01-14
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-01-05
相关资源
最近更新 更多