Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1wfupg-005mmt-0i for pgsql-hackers@arkaria.postgresql.org; Sat, 04 Jul 2026 07:30:36 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.96) (envelope-from ) id 1wfuoe-009qVA-2C for pgsql-hackers@arkaria.postgresql.org; Sat, 04 Jul 2026 07:29:32 +0000 Received: from makus.postgresql.org ([2001:4800:3e1:1::229]) by malur.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1wfuoe-009qV2-19 for pgsql-hackers@lists.postgresql.org; Sat, 04 Jul 2026 07:29:32 +0000 Received: from meldrar.postgresql.org ([2a02:c0:301:0:ffff::31]) by makus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.98.2) (envelope-from ) id 1wfuoZ-00000001QYc-0UtF for pgsql-hackers@postgresql.org; Sat, 04 Jul 2026 07:29:31 +0000 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=postgresql.org; s=20171124; h=Content-Transfer-Encoding:Content-Type: Mime-Version:References:In-Reply-To:From:Subject:Cc:To:Message-Id:Date:Sender :Reply-To:Content-ID:Content-Description; bh=ZmNaJrhKcGv7DMaWYxpdKxynWhS9Pc3B4vb/+AQrK+g=; b=t/an14tLKZHdjhNtmYIjUaYh3K eg92WPiOXEkjUtGq5JSXdWr0W/LF206GlAXz67wDUNyL20qHMcYkPmAjihdZPdHAAHPr8lZ5Ei95V Cazrulz1gH5VVgtQTaTPtsNUbwNN9f1ZdQSE/YqkbFkES2oUnJmDWO/0SsNlZSw0F8Ce+gwuyex8B k4BfsgTCchtN/noPvuGZMAa7Vpliy+b4mh75zmkpIfv+9DjsxooiFvm0c+e8zHtyVbE+HG1IZzGhq VSw3Fcsfjy8R6xNSTQ1gCbcg6QVT2Gak8J1FK+Vj4ddah4AdhipgXqLzgBTDw0GyG/OaG7+bmfW6L fnzZjRZQ==; Received: from [2409:11:4120:300:2325:f28e:c3a9:605c] (helo=localhost) by meldrar.postgresql.org with esmtpsa (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1wfuoT-009kWo-0L; Sat, 04 Jul 2026 07:29:25 +0000 Date: Sat, 04 Jul 2026 16:28:41 +0900 (JST) Message-Id: <20260704.162841.39857602849942465.ishii@postgresql.org> To: assam258@gmail.com Cc: jian.universality@gmail.com, pgsql-hackers@postgresql.org, zsolt.parragi@percona.com, sjjang112233@gmail.com, vik@postgresfriends.org, er@xs4all.nl, jacob.champion@enterprisedb.com, david.g.johnston@gmail.com, peter@eisentraut.org, li.evan.chao@gmail.com Subject: Re: Row pattern recognition From: Tatsuo Ishii In-Reply-To: References: <20260701.211805.2273383346456030984.ishii@postgresql.org> <20260703.211309.1130370315247638762.ishii@postgresql.org> X-Mailer: Mew version 6.8 on Emacs 29.3 Mime-Version: 1.0 Content-Type: Text/Plain; charset=us-ascii Content-Transfer-Encoding: 7bit X-Host-Lookup-Failed: Reverse DNS lookup failed for 2409:11:4120:300:2325:f28e:c3a9:605c (failed) List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk > The change is a simplification that came out of Jian's v48 review, and it > does not change the cost the model produces. > > It follows Jian's suggestion from 2026-06-15 [1]: > >> collectPatternVariables is not needed. >> The parser already ensures every DEFINE variable appears in PATTERN, >> so there is nothing to filter. >> Also, we don't really do anything special (like make a dummy Const) >> regarding PATTERN variables that not appearing in the DEFINE clause. > > The two loops charge exactly the same set, for the following reason: > > - The old loop walked the unique PATTERN variables (collectPatternVariables > deduplicates, returning each name once) and, for each, looked up the > matching DEFINE entry by resname and charged that DEFINE's cost. > - Every DEFINE variable is guaranteed to appear in PATTERN -- the parser > rejects a DEFINE variable that is not used in PATTERN (errmsg "DEFINE > variable \"%s\" is not used in PATTERN" in parse_rpr.c). So the DEFINE > clause is always a subset of the unique PATTERN variables, and each > DEFINE resname is unique. > - A PATTERN variable that has no DEFINE contributes nothing to the old > loop, because the inner resname lookup finds no match. > > So the old loop already charged each DEFINE expression exactly once, and > nothing else. Iterating defineClause directly, as v50-0006 does, visits > precisely that same set once each. The estimate is unchanged; only the > redundant outer walk over PATTERN and the per-variable resname lookup into > the DEFINE clause are removed. Ok, thanks for the explanation. > This also matches the premise of the cost model we settled on back in > February: the NFA executor evaluates every DEFINE expression once per row, > so the natural unit for the per-tuple charge is the DEFINE variable. BTW, I was thinking about cases where same DEFINE variable appears twice or more in PATTERN for a same row. For example PATTERN (A|A). But in this case it would be optimized out to (A). So we don't need to worry about A appearing twice. So our cost model is correct in this case. Regards, -- Tatsuo Ishii SRA OSS K.K. English: http://www.sraoss.co.jp/index_en/ Japanese:http://www.sraoss.co.jp