LAST_VALUE returns the entire partition - Mailing list pgsql-sql

From Дмитрий Иванов
Subject LAST_VALUE returns the entire partition
Date
Msg-id CAPL5KHp2AfXb_xi+-gpffaS1-idNarvxFuUOqkCs+rq-yWz1Lw@mail.gmail.com
Whole thread Raw
Responses Re: LAST_VALUE returns the entire partition  (Tom Lane <tgl@sss.pgh.pa.us>)
List pgsql-sql
Hi!
I cannot understand the behavior of the last_value function. Conditions opposite to first_value conditions. Why such a result?

first_value(rg.spath) OVER (PARTITION BY rg.id_path ORDER BY rg.level DESC) AS first_value <> last_value(rg.spath) OVER (PARTITION BY rg.id_path ORDER BY rg.level) AS last_value?

**************************************************************
SELECT * FROM VERSION();
--
version
PostgreSQL 12.7, compiled by Visual C++ build 1914, 64-bit

**************************************************************
CREATE TABLE "public"."group" (
"id" BigInt NOT NULL,
"id_parent" BigInt NOT NULL,
"name" Character Varying( 100 ) NOT NULL,
PRIMARY KEY ( "id" ) );

**************************************************************
SELECT * FROM public.group;
--
 id  | id_parent |     name
-----+-----------+---------------
 386 |       385 | group_level_3
 385 |       384 | group_level_2
 384 |       383 | group_level_1
 383 |         0 | group_root
(4 строки)

**************************************************************
CREATE OR REPLACE VIEW "public"."group_path_first" AS  WITH RECURSIVE rgroup(id_path, id, id_parent, level, path, spath, cycle) AS (
         SELECT rg.id,
            rg.id,
            rg.id_parent,
            0,
            ARRAY[rg.id] AS "array",
            concat(rg.name) AS concat,
            false AS bool
           FROM "group" rg
          WHERE (rg.id = 386)
        UNION ALL
         SELECT rgroup_1.id_path,
            rgc.id,
            rgc.id_parent,
            (rgroup_1.level + 1),
            (ARRAY[rgc.id] || rgroup_1.path),
            concat(rgc.name, $$\$$, rgroup_1.spath) AS concat,
            (rgc.id = ANY (rgroup_1.path))
           FROM ("group" rgc
             JOIN rgroup rgroup_1 ON ((rgroup_1.id_parent = rgc.id)))
          WHERE (NOT rgroup_1.cycle)
        ), grouppath(id_path, spath) AS (
         SELECT DISTINCT rg.id_path,
            first_value(rg.spath) OVER (PARTITION BY rg.id_path ORDER BY rg.level DESC) AS first_value
           FROM rgroup rg
        )
 SELECT grouppath.id_path,
    grouppath.spath
   FROM grouppath;
-- -------------------------------------------------------------
SELECT * FROM "public"."group_path_first";
--
 id_path |                        spath
---------+------------------------------------------------------
     386 | group_root\group_level_1\group_level_2\group_level_3
(1 строка)

**************************************************************
CREATE OR REPLACE VIEW "public"."group_path_last" AS  WITH RECURSIVE rgroup(id_path, id, id_parent, level, path, spath, cycle) AS (
         SELECT rg.id,
            rg.id,
            rg.id_parent,
            0,
            ARRAY[rg.id] AS "array",
            concat(rg.name) AS concat,
            false AS bool
           FROM public."group" rg
           WHERE rg.id = 386
        UNION ALL
         SELECT rgroup_1.id_path,
            rgc.id,
            rgc.id_parent,
            (rgroup_1.level + 1),
            (ARRAY[rgc.id] || rgroup_1.path),
            concat(rgc.name, $$\$$, rgroup_1.spath) AS concat,
            (rgc.id = ANY (rgroup_1.path))
           FROM (public."group" rgc
             JOIN rgroup rgroup_1 ON ((rgroup_1.id_parent = rgc.id)))
          WHERE (NOT rgroup_1.cycle)
        ),
        grouppath(id_path, spath) AS (
         SELECT DISTINCT rg.id_path,
            last_value(rg.spath) OVER (PARTITION BY rg.id_path ORDER BY rg.level) AS last_value
           FROM rgroup rg
        )
 SELECT * FROM grouppath;
-- -------------------------------------------------------------
SELECT * FROM "public"."group_path_last";
--
 id_path |                        spath
---------+------------------------------------------------------
     386 | group_root\group_level_1\group_level_2\group_level_3
     386 | group_level_3
     386 | group_level_2\group_level_3
     386 | group_level_1\group_level_2\group_level_3
(4 строки)

pgsql-sql by date:

Previous
From: "Dean Gibson (DB Administrator)"
Date:
Subject: Re: Help to design relations between some 5 tables with possible many-to-many relations
Next
From: Tom Lane
Date:
Subject: Re: LAST_VALUE returns the entire partition