From 935e5879a8363e3e86721e2cb9df5bc0e46b0117 Mon Sep 17 00:00:00 2001 From: ChronicallyJD Date: Fri, 7 Aug 2026 14:39:47 -0600 Subject: [PATCH 1/2] docs(#485): the analyze() comment still claimed null_frac comes from the zone maps #488 moved null_frac off the zone maps and onto the same read as n_distinct, because the zone-map counts describe what was written and a DELETE left the fraction normalised against rows the table no longer held. It did not update the COMMENT ON FUNCTION, which still tells the user the opposite: taking null_frac exactly from the zone maps rather than sampling That is my own omission from #488. It is user-visible through \df+ and through the extension script, and it is the kind of stale claim that is believed because it is adjacent to correct code. The replacement says what is now true and adds the property that matters more than the source: null_frac, n_distinct and the most-common frequencies all come from one read, so they describe one population. That identity is what #485 was actually about. Co-Authored-By: Claude Opus 5 (1M context) Claude-Session: https://claude.ai/code/session_01QRQYekvivA4RLDnndhanHK --- pgcolumnar--1.0-alpha.sql | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pgcolumnar--1.0-alpha.sql b/pgcolumnar--1.0-alpha.sql index c7d2da4..16d0ed9 100644 --- a/pgcolumnar--1.0-alpha.sql +++ b/pgcolumnar--1.0-alpha.sql @@ -1425,4 +1425,4 @@ END; $$; COMMENT ON FUNCTION pgcolumnar.analyze(regclass, text[]) - IS 'collect per-column statistics by reading one column at a time, taking null_frac exactly from the zone maps rather than sampling (#414); core ANALYZE remains the correctness path and nothing schedules this, see #415'; + IS 'collect per-column statistics by reading one column at a time rather than sampling every column (#414); null_frac, n_distinct and the most-common frequencies all come from that read, so they describe one population (#485); core ANALYZE remains the correctness path and nothing schedules this, see #415'; From 54f6b0394f06426aaedbaf05a4e1b505efcf1f93 Mon Sep 17 00:00:00 2001 From: ChronicallyJD Date: Fri, 7 Aug 2026 17:26:38 -0600 Subject: [PATCH 2/2] docs(#485): the same claim survived in the function header, 443 lines up Review catch. The header comment at :985 said null_frac from the zone maps (metadata only, no data read) which is a stronger claim than the COMMENT ON FUNCTION this branch already fixed: it does not merely name the source, it promises no data read. After #488 that read always happens. It survived my own sweep because it wraps across two lines, so a single-line grep for the phrase cannot match it. Re-swept the whole tree with a multi-line pattern; the only remaining occurrences are past-tense history in this file and in test/analyze_function.sh, plus #488's note at :1352 explaining why nv is NOT derived from a zone-map null_frac, which is correct and stays. Rewritten to lead with the property rather than the source: all of it exact, all of it from ONE read, which is what makes every statistic describe one population. Co-Authored-By: Claude Opus 5 (1M context) Claude-Session: https://claude.ai/code/session_01QRQYekvivA4RLDnndhanHK --- pgcolumnar--1.0-alpha.sql | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/pgcolumnar--1.0-alpha.sql b/pgcolumnar--1.0-alpha.sql index 16d0ed9..af789fb 100644 --- a/pgcolumnar--1.0-alpha.sql +++ b/pgcolumnar--1.0-alpha.sql @@ -982,10 +982,15 @@ COMMENT ON FUNCTION pgcolumnar.parallel_copy(regclass, text, int) * an opt-in accelerator for wide tables and, like pgcolumnar.vacuum(), nothing * schedules it: see #415. * - * Collected so far, all of it exact rather than sampled: null_frac from the zone - * maps (metadata only, no data read), n_distinct from reading one column, and - * from that same read the most-common values with their frequencies and a - * histogram of what remains once those are excluded. + * Collected so far, all of it exact rather than sampled, and all of it from ONE + * read of the column: null_frac, n_distinct, the most-common values with their + * frequencies, and a histogram of what remains once those are excluded. + * + * One read is the property that matters, not merely the source of each number. + * null_frac came from the zone maps until #485, which was cheaper and was wrong + * after a DELETE, because those counts describe what was written. Taking it from + * the same read as the rest is what makes every statistic here describe one + * population, which is the identity the planner's selectivity arithmetic needs. * * "Exact" is the whole difference and it is not a refinement of core's numbers. * Core samples 30,000 rows, so a value held by one row in 500,000 is missed