Re: Performance query about large tables, lots of concurrent access - Mailing list pgsql-performance

From Karl Wright
Subject Re: Performance query about large tables, lots of concurrent access
Date
Msg-id 4677F617.5000105@metacarta.com
Whole thread Raw
In response to Re: Performance query about large tables, lots of concurrent access  (Tom Lane <tgl@sss.pgh.pa.us>)
Responses Re: Performance query about large tables, lots of concurrent access
Re: Performance query about large tables, lots of concurrent access
List pgsql-performance
Tom Lane wrote:
> Karl Wright <kwright@metacarta.com> writes:
>> [2007-06-18 09:39:49,797]ERROR  Plan: Index Scan using i1181764142395 on
>> intrinsiclink  (cost=0.00..14177.29 rows=5 width=253)
>> [2007-06-18 09:39:49,797]ERROR  Plan:   Index Cond: ((jobid = $2) AND
>> ((childidhash)::text = ($3)::text))
>> [2007-06-18 09:39:49,797]ERROR  Plan:   Filter: ((childid = ($4)::text)
>> AND ((isnew = ($5)::bpchar) OR (isnew = ($6)::bpchar)))
>
>>> In this case it looks like the planner is afraid that that's exactly
>>> what will happen --- a cost of 14177 suggests that several thousand row
>>> fetches are expected to happen, and yet it's only predicting 5 rows out
>>> after the filter.
>
>> Well, that's odd, because the hash in question that it is using is the
>> SHA-1 hash of a URL.  There's essentially one row per URL in this table.
>
> What about isnew?

Isnew is simply a flag which I want to set for all rows that belong to
this particular child, but only if it's one of two particular values.

>
> Also, how many rows do *you* expect out of the query?  The planner is
> not going to be aware of the hashed relationship between childidhash
> and childid --- it'll think those are independent conditions which they
> evidently aren't.  So it may be that the query really does retrieve
> thousands of rows, and the rows=5 estimate is bogus because it's
> double-counting the selectivity of the childid condition.
>

This can vary, but I expect there to be at on average a few dozen rows
returned from the overall query.  The only way the index-condition part
of the query can be returning thousands of rows would be if: (a) there
is really a lot of data of this kind, or (b) the hash function is
basically not doing its job and there are thousands of collisions occurring.

In fact, that's not the case. In psql I just did the following analysis:

 >>>>>>
metacarta=> explain select count(*) from intrinsiclink where
jobid=1181766706097 and
childidhash='7E130F3B688687757187F1638D8776ECEF3009E0';
                                                              QUERY PLAN


------------------------------------------------------------------------------------------------------------------------------------
  Aggregate  (cost=14992.23..14992.24 rows=1 width=0)
    ->  Index Scan using i1181764142395 on intrinsiclink
(cost=0.00..14971.81 rows=8167 width=0)
          Index Cond: ((jobid = 1181766706097::bigint) AND
((childidhash)::text = '7E130F3B688687757187F1638D8776ECEF3009E0'::text))
(3 rows)

metacarta=> select count(*) from intrinsiclink where jobid=1181766706097
and childidhash='7E130F3B688687757187F1638D8776ECEF3009E0';
  count
-------
      0
(1 row)
<<<<<<

Granted this is well after-the-fact, but you can see that the cost
estimate is wildly wrong in this case.

I did an ANALYZE on that table and repeated the explain, and got this:

 >>>>>>
metacarta=> analyze intrinsiclink;
ANALYZE
metacarta=> explain select count(*) from intrinsiclink where
jobid=1181766706097 and
childidhash='7E130F3B688687757187F1638D8776ECEF3009E0';
                                                              QUERY PLAN


------------------------------------------------------------------------------------------------------------------------------------
  Aggregate  (cost=15276.36..15276.37 rows=1 width=0)
    ->  Index Scan using i1181764142395 on intrinsiclink
(cost=0.00..15255.53 rows=8333 width=0)
          Index Cond: ((jobid = 1181766706097::bigint) AND
((childidhash)::text = '7E130F3B688687757187F1638D8776ECEF3009E0'::text))
(3 rows)
<<<<<<

... even more wildly wrong.

Karl

>             regards, tom lane
>


pgsql-performance by date:

Previous
From: Chris Browne
Date:
Subject: Re: Maintenance question / DB size anomaly...
Next
From: Francisco Reyes
Date:
Subject: Re: Hardware suggestions