Присоединяйтесь к максимальным записям в Postresql - PullRequest
0 голосов
/ 25 января 2019

У меня есть две таблицы:

products
+----+--------+
| id | name   |
+----+--------+
| 1  | Orange |
| 2  | Juice  |
| 3  | Fance  |
+----+--------+
reviews
+----+------------+-------+------------+
| id | created_at | price | product_id |
+----+------------+-------+------------+
| 1  | 12/12/20   | 2     | 1          |
| 2  | 12/14/20   | 4     | 1          |
| 3  | 12/15/20   | 5     | 2          |
+----+------------+-------+------------+

Как получить список товаров, упорядоченных по цене самого последнего обзора (макс. Созданного):

+------------+--------+-----------+-------+
| product_id | name   | review_id | price |
+------------+--------+-----------+-------+
| 2          | Juice  | 3         | 5     |
| 1          | Orance | 2         | 4     |
| 3          | Fance  |           |       |
+------------+--------+-----------+-------+

Я использую последнюю версию PostgreSQL.

Ответы [ 2 ]

0 голосов
/ 25 января 2019

DISTINCT ON и внешнее соединение - хороший подход, но я бы обработал это как:

SELECT . . .  -- whatever columns you want
FROM products p LEFT JOIN
     (SELECT DISTINCT ON (r.product_id) r.*
      FROM reviews r
      ORDER BY r.product_id, r.created_at DESC NULLS LAST
     ) r
     ON r.product_id = p.id
ORDER BY p.price DESC NULLS LAST;

Разница в выполнении DISTINCT ON до JOIN или после может выглядеть незначительной. Но эта версия запроса может использовать индекс на reviews(product_id, created_at desc). И это может стать большим выигрышем в производительности для большого количества данных.

Индексы нельзя использовать для ORDER BY, который смешивает столбцы из разных таблиц.

0 голосов
/ 25 января 2019

demo: db <> fiddle

Использование DISTINCT ON

SELECT
    *
FROM (
    SELECT DISTINCT ON (p.id)
        p.id,
        p.name,
        r.id as review_id,
        r.price
    FROM
        reviews r
    RIGHT JOIN products p ON r.product_id = p.id
    ORDER BY p.id, r.created_at DESC NULLS LAST
) s
ORDER BY price DESC NULLS LAST
  1. Соединить обе таблицы (products LEFT JOIN review или review RIGHT JOIN products).
  2. Теперь вы должны выполнять свои заказы.Сначала вы хотите сгруппировать продукты вместе.Затем вы хотите получить самую последнюю запись для каждого продукта (дату в порядке убывания, чтобы получить самую последнюю в качестве первой строки).
  3. DISTINCT ON всегда фильтрует первую строку упорядоченной группы.Таким образом, вы получаете самую последнюю запись по продукту.
  4. Чтобы отсортировать строки вашего продукта, поместите 1-3 в подзапрос и закажите price впоследствии.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...