Следующий запрос занимает более 7 минут в PostgreSQL 11.1:
SELECT
'2019-01-19' as date,
'2019-01-19'::date - generate_series(first_observed, last_observed, interval '1 day')::date as days_to_date,
ROUND(AVG(price)) as price,
area_id
FROM
table_example
GROUP BY
days_to_date, area_id;
table_example
содержит около 15 миллионов строк.
Есть ли способы его оптимизировать? Я уже добавил следующие индексы:
CREATE INDEX ON table_example (first_observed, last_observed);
CREATE INDEX ON table_example (area_id);
Это вывод из EXPLAIN (ANALYZE,BUFFERS)
:
GroupAggregate (cost=3235559683.68..3377398628.68 rows=1418000 width=72) (actual time=334933.966..440096.869 rows=21688 loops=1)
Group Key: (('2019-01-19'::date - ((generate_series((first_observed)::timestamp with time zone, (last_observed)::timestamp with time zone, '1 day'::interval)))::date)), area_id
Buffers: local read=118167 dirtied=118167 written=117143, temp read=1634631 written=1635058
-> Sort (cost=3235559683.68..3271009671.18 rows=14179995000 width=40) (actual time=334923.933..391690.184 rows=380203171 loops=1)
Sort Key: (('2019-01-19'::date - ((generate_series((first_observed)::timestamp with time zone, (last_observed)::timestamp with time zone, '1 day'::interval)))::date)), area_id
Sort Method: external merge Disk: 9187584kB
Buffers: local read=118167 dirtied=118167 written=117143, temp read=1634631 written=1635058
-> Result (cost=0.00..390387079.39 rows=14179995000 width=40) (actual time=214.798..171717.941 rows=380203171 loops=1)
Buffers: local read=118167 dirtied=118167 written=117143
-> ProjectSet (cost=0.00..71337191.89 rows=14179995000 width=44) (actual time=214.796..102823.749 rows=380203171 loops=1)
Buffers: local read=118167 dirtied=118167 written=117143
-> Seq Scan on table_example (cost=0.00..259966.95 rows=14179995 width=44) (actual time=0.031..2449.511 rows=14179995 loops=1)
Buffers: local read=118167 dirtied=118167 written=117143
Planning Time: 0.409 ms
JIT:
Functions: 18
Options: Inlining true, Optimization true, Expressions true, Deforming true
Timing: Generation 5.034 ms, Inlining 13.010 ms, Optimization 121.440 ms, Emission 79.996 ms, Total 219.480 ms
Execution Time: 441133.410 ms
Вот как выглядит table_example:
column name data type
'house_pk' 'integer'
'date_in' 'date'
'first_observed' 'date'
'last_observed' 'date'
'price' 'numeric'
'area_id' 'integer'
Существует 60 различных идентификаторов областей.
Запрос выполняется на многоядерной машине (24 ядра) с 128 ГБ памяти. Однако возможно, что настройки не оптимальны.
CREATE TABLE
с типами данных и ограничениями. Плюс выводEXPLAIN (ANALYZE, BUFFERS)
. См.: stackoverflow.com/tags/postgresql-performance/info Вам нужны результаты за все дни и все области в однажды? У вас есть таблицаarea
с 1 строкой на соответствующийarea_id
? Сколько различныхarea_id
? Сколько дней междуfirst_observed
иlast_observed
- мин./макс./среднее? - person Erwin Brandstetter   schedule 18.01.2019EXPLAIN (ANALYZE, BUFFERS)
. 2) Мне нужны результаты за все дни сразу. Я мог бы сделать несколько запросов для областей, но это потребовало бы выполнения 60 запросов вместо одного. 3) Я не уверен, что вы имеете в виду. У меня есть таблица, содержащая area_ids с одной строкой на area_id. Это то, что ты имеешь в виду? 4) 60 идентификаторов областей, 5) мин. = 0, макс. = 335, среднее = 25,8 - person Wessi   schedule 18.01.2019CREATE TABLE
— это способ раскрытия информации о вашей таблице. Пример: stackoverflow.com/questions/9789736/ Различные клиенты (включая pgAdmin3 и pgAdmin4) отображают обратно спроектированный оператор. - person Erwin Brandstetter   schedule 18.01.2019