Выберите одну строку внутри группы в соответствии с критериями в PostgreSQL - PullRequest
0 голосов
/ 31 мая 2019

У меня есть таблица как таковая (tbl):

+----+-----+------+-----+
| pk | grp | attr | val |
+----+-----+------+-----+
|  0 |   0 | ohif |   4 |
|  1 |   0 | foha |  56 |
|  2 |   0 | slns |   2 |
|  3 |   1 | faso |  11 |
|  4 |   1 | tepj |   4 |
|  5 |   2 | bnda |  12 |
|  6 |   2 | ojdf |   9 |
|  7 |   2 | anaw |   1 |
+----+-----+------+-----+

Я бы хотел выбрать по одной строке из каждой группы, в частности, с максимальной val для каждой группы.

Я могу легко выбрать grp и val:

SELECT grp, MAX(val)
FROM tbl
GROUP BY grp

Выход из этой таблицы (tbl2):

+-----+-----+
| grp | val |
+-----+-----+
|   0 |  56 |
|   1 |  11 |
|   2 |  12 |
+-----+-----+

Однако я хочу эту таблицу:

+----+-----+------+-----+
| pk | grp | attr | val |
+----+-----+------+-----+
|  1 |   0 | foha |  56 |
|  3 |   1 | faso |  11 |
|  5 |   2 | bnda |  12 |
+----+-----+------+-----+

Поскольку ключ (grp, val) представляет собой ключ, я мог бы присоединиться к tbl2 слева с tbl на тех же grp и val.

Однако мне было интересно, было ли какое-то другое решение: в моей реальной ситуации tbl - довольно сложная и тяжелая производная таблица, и у меня есть ограничение дизайна, заключающееся в невозможности использования временных таблиц. Есть ли способ упорядочить строки внутри каждой группы в соответствии с val и затем взять первую запись для каждой группы?

Я нахожусь на PostgreSQL 10, но лучше всего было бы использовать стандартное решение SQL.

1 Ответ

2 голосов
/ 31 мая 2019

В Postgres лучший подход - distinct on:

SELECT DISTINCT ON (t.grp) t.*
FROM tbl
ORDER BY grp, val DESC;

В частности, это может использовать индекс на (grp, val desc).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...