snippetsqlMinor
Improve sort performance in PostgreSQL?
Viewed 0 times
improvesortpostgresqlperformance
Problem
I've got a simple blog database in postgres-8.4 which has two tables,
None of these tables is particularly large, and yet that query takes 46ms. The execution plan is:
```
Limit (cost=119.54..119.58 rows=1 width=1150) (actual time=46.479..46.481 rows=1 loops=1)
-> GroupAggregate (cost=119.54..138.88 rows=455 width=1150) (actual time=46.475..46.475 rows=1 loops=1)
-> Sort (cost=119.54..120.68 rows=455 width=1150) (actual time=46.426..46.428 rows=2 loops=1)
Sort Key: articles.datestamp, articles.id, articles.title, articles.shorttitle, articles.description, articles.markdown, articles.body, articles.idxfti, articles.published, articles.type
Sort Method: quicksort Memory: 876kB
-> Hash Left Join (cost=11.34..99.45 rows=455 width=1150) (actual time=0.513..2.527 rows=566 loops=1)
Hash Cond: (articles.id = comments.article_id)
-> Seq Scan on articles (cost=0.00..78.84 rows=455 width=1146) (actual time=0.017..0.881 rows=455 loops=1)
Filter: ((type)::text = 'NEWS'::text)
-> Hash (c
articles and comments. I have a query (generated by Django) that wants to get the latest article of type 'NEWS' and also find the number of comments for that article. It does that with the following query:SELECT "articles"."id", "articles"."datestamp", "articles"."title", "articles"."shorttitle", "articles"."description", "articles"."markdown", "articles"."body", "articles"."idxfti", "articles"."published", "articles"."type", COUNT("comments"."id") AS "comment__count"
FROM "articles"
LEFT OUTER JOIN "comments" ON ("articles"."id" = "comments"."article_id")
WHERE ("articles"."type"='NEWS')
GROUP BY "articles"."id", "articles"."datestamp", "articles"."title", "articles"."shorttitle", "articles"."description", "articles"."markdown", "articles"."body", "articles"."idxfti", "articles"."published", "articles"."type"
ORDER BY "articles"."datestamp" DESC
LIMIT 1;None of these tables is particularly large, and yet that query takes 46ms. The execution plan is:
```
Limit (cost=119.54..119.58 rows=1 width=1150) (actual time=46.479..46.481 rows=1 loops=1)
-> GroupAggregate (cost=119.54..138.88 rows=455 width=1150) (actual time=46.475..46.475 rows=1 loops=1)
-> Sort (cost=119.54..120.68 rows=455 width=1150) (actual time=46.426..46.428 rows=2 loops=1)
Sort Key: articles.datestamp, articles.id, articles.title, articles.shorttitle, articles.description, articles.markdown, articles.body, articles.idxfti, articles.published, articles.type
Sort Method: quicksort Memory: 876kB
-> Hash Left Join (cost=11.34..99.45 rows=455 width=1150) (actual time=0.513..2.527 rows=566 loops=1)
Hash Cond: (articles.id = comments.article_id)
-> Seq Scan on articles (cost=0.00..78.84 rows=455 width=1146) (actual time=0.017..0.881 rows=455 loops=1)
Filter: ((type)::text = 'NEWS'::text)
-> Hash (c
Solution
Another way to rewrite the query, with an inline subquery:
SELECT id,
datestamp,
title,
shorttitle,
description,
markdown,
body,
idxfti,
published,
type,
( SELECT COUNT(*)
FROM comments
WHERE articles.id = comments.article_id
) AS comment__count
FROM articles
WHERE type = 'NEWS'
ORDER BY datestamp DESC
LIMIT 1Code Snippets
SELECT id,
datestamp,
title,
shorttitle,
description,
markdown,
body,
idxfti,
published,
type,
( SELECT COUNT(*)
FROM comments
WHERE articles.id = comments.article_id
) AS comment__count
FROM articles
WHERE type = 'NEWS'
ORDER BY datestamp DESC
LIMIT 1Context
StackExchange Database Administrators Q#17209, answer score: 9
Revisions (0)
No revisions yet.