Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1hhD8y-00089c-M5 for pgsql-hackers@arkaria.postgresql.org; Sat, 29 Jun 2019 13:11:52 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.89) (envelope-from ) id 1hhD8x-00023u-53 for pgsql-hackers@arkaria.postgresql.org; Sat, 29 Jun 2019 13:11:51 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1hhD8w-00023n-Si for pgsql-hackers@lists.postgresql.org; Sat, 29 Jun 2019 13:11:50 +0000 Received: from mail-wm1-x342.google.com ([2a00:1450:4864:20::342]) by magus.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1hhD8p-0005AJ-Ia for pgsql-hackers@lists.postgresql.org; Sat, 29 Jun 2019 13:11:50 +0000 Received: by mail-wm1-x342.google.com with SMTP id s3so11596916wms.2 for ; Sat, 29 Jun 2019 06:11:42 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=2ndquadrant-com.20150623.gappssmtp.com; s=20150623; h=date:from:to:cc:subject:message-id:references:mime-version :content-disposition:in-reply-to:user-agent; bh=4Km0PtLG7zdPzCsZUDDTouHLGsnC0nZX71mgXUG8Z9Y=; b=QToG8bwbT/XJFy4bi13hlcJtE5hFZjQiT76W3mRSgPK2Tg/vdY5vXqCMGSosQHsyv+ kIEzrbXAXvaS61SBQ4tOGHa9Pf3xRgCYHCih1V6KSvmOGj0DoNqkOCxEuMDNwStycSUt i5V7QwpMFQIz5XS+4p13d+E9WpMI6z7qCo/qmgW0btp6PR19wPuOqBfOS1FbtL9puxqa JzH3iWQPE8jsq+0joCMxSR1OkjuKFqm2CXZJ0tOm4IhbZtPnwGmZk4KLobW3aR054vG0 q20auy+rtXsWpMn7/103cG3H7fnKlD8o1s70ichDEMd4seTxwfircEoGqmtjFi87THqc uiOA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:in-reply-to:user-agent; bh=4Km0PtLG7zdPzCsZUDDTouHLGsnC0nZX71mgXUG8Z9Y=; b=T1+uKyN3zT6ou8bZDw0szCQQZ/pjvtNfMXXqFRh4Sur/qhLrG3/TWT56f6PPhLjWS7 Ys9PeznwAZkZf1uXFXua2j3p4YMsVXMd3nAQDb9rK43vjiTREbIMJkqCD4wggCB2V0G5 bjq8vIUPlZnEjzF9NmG6EO0BDjMapyYZVR/+31BHzwaACFW79/zWFWBXfS//IZoQ1TnT YKyX41Yw5loVFfu3WT8sPgg4OWDDk741rnQJ0QA1CQm4QGwJKKTbcSM15MJ0qvg2+lZ9 k3azejxDqPNWsJpfUp7olJaxl927tDuzlvIi32yoCNxIJAbgrXLXelMpnIPV8Pj6oncX RjNQ== X-Gm-Message-State: APjAAAXeF8sRWUjsSANhoXKkbw1Hxw8RELlbnqh77qf2JYjgh5y3tIfn PmitsH+F+m38obn8q1T19Yx/KA== X-Google-Smtp-Source: APXvYqy/hvwZt+YpDPwdnqGrFwzZbX1xVVkB4SfSiDT//wwQhCTV0MiUdtZPSZvzjZ+I6Pe4J4hXZQ== X-Received: by 2002:a7b:c356:: with SMTP id l22mr3669063wmj.97.1561813901946; Sat, 29 Jun 2019 06:11:41 -0700 (PDT) Received: from localhost (ip-86-49-253-160.net.upcbroadband.cz. [86.49.253.160]) by smtp.gmail.com with ESMTPSA id j189sm5914847wmb.48.2019.06.29.06.11.37 (version=TLS1_3 cipher=AEAD-AES256-GCM-SHA384 bits=256/256); Sat, 29 Jun 2019 06:11:37 -0700 (PDT) Date: Sat, 29 Jun 2019 15:11:35 +0200 From: Tomas Vondra To: Julien Rouhaud Cc: Nikita Glukhov , PostgreSQL Hackers , Tom Lane , Marc Cousin Subject: Re: Avoid full GIN index scan when possible Message-ID: <20190629131135.ilktnqtollvbfnml@development> References: <20190628161051.szk2kxmue6yjdmra@development> <4547.1561748599@sss.pgh.pa.us> <20190628195401.frwhcga76rrytbc4@development> <7773.1561752983@sss.pgh.pa.us> <20190629102514.ucfzglxu7ccjsbjr@development> MIME-Version: 1.0 Content-Type: text/plain; charset=us-ascii; format=flowed Content-Disposition: inline In-Reply-To: User-Agent: NeoMutt/20180716-1444-295967 List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Precedence: bulk On Sat, Jun 29, 2019 at 02:50:51PM +0200, Julien Rouhaud wrote: >On Sat, Jun 29, 2019 at 12:25 PM Tomas Vondra > wrote: >> >> On Sat, Jun 29, 2019 at 11:10:03AM +0200, Julien Rouhaud wrote: >> >On Sat, Jun 29, 2019 at 12:51 AM Nikita Glukhov >> >> -- patched >> >> EXPLAIN ANALYZE SELECT * FROM test WHERE t LIKE '%1234%' AND t LIKE '%1%'; >> >> QUERY PLAN >> >> ----------------------------------------------------------------------------------------------------------------------- >> >> Bitmap Heap Scan on test (cost=20.43..176.79 rows=42 width=6) (actual time=0.287..0.424 rows=300 loops=1) >> >> Recheck Cond: ((t ~~ '%1234%'::text) AND (t ~~ '%1%'::text)) >> >> Rows Removed by Index Recheck: 2 >> >> Heap Blocks: exact=114 >> >> -> Bitmap Index Scan on test_t_idx (cost=0.00..20.42 rows=42 width=0) (actual time=0.271..0.271 rows=302 loops=1) >> >> Index Cond: ((t ~~ '%1234%'::text) AND (t ~~ '%1%'::text)) >> >> Planning Time: 0.080 ms >> >> Execution Time: 0.450 ms >> >> (8 rows) >> > >> >One thing that's bothering me is that the explain implies that the >> >LIKE '%i% was part of the index scan, while in reality it wasn't. One >> >of the reason why I tried to modify the qual while generating the path >> >was to have the explain be clearer about what is really done. >> >> Yeah, I think that's a bit annoying - it'd be nice to make it clear >> which quals were actually used to scan the index. It some cases it may >> not be possible (e.g. in cases when the decision is done at runtime, not >> while planning the query), but it'd be nice to show it when possible. > >Maybe we could somehow add some runtime information about ignored >quals, similar to the "never executed" information for loops? > Maybe. I suppose it depends on when exactly we make the decision about which quals to ignore. >> A related issue is that during costing is too late to modify cardinality >> estimates, so the 'Bitmap Index Scan' will be expected to return fewer >> rows than it actually returns (after ignoring the full-scan quals). >> Ignoring redundant quals (the way btree does it at execution) does not >> have such consequence, of course. >> >> Which may be an issue, because we essentially want to modify the list of >> quals to minimize the cost of >> >> bitmap index scan + recheck during bitmap heap scan >> >> OTOH it's not a huge issue, because it won't affect the rest of the plan >> (because that uses the bitmap heap scan estimates, and those are not >> affected by this). > >Doesn't this problem already exists, as the quals that we could drop >can't actually reduce the node's results? How could it not reduce the node's results, if you ignore some quals that are not redundant? My understanding is we have a plan like this: Bitmap Heap Scan -> Bitmap Index Scan and by ignoring some quals at the index scan level, we trade the (high) cost of evaluating the qual there for a plain recheck at the bitmap heap scan. But it means the index scan may produce more rows, so it's only a win if the "extra rechecks" are cheaper than the (removed) full scan. So the full scan might actually reduce the number of rows from the index scan, but clearly whatever we do the results from the bitmap heap scan must remain the same. regards -- Tomas Vondra http://www.2ndQuadrant.com PostgreSQL Development, 24x7 Support, Remote DBA, Training & Services