PostgreSQL
 sql >> Datenbank >  >> RDS >> PostgreSQL

Wie vergleiche ich die aktuelle Zeile mit der nächsten und vorherigen Zeile in PostgreSQL?

Dies ist meine Lösung mit WINDOW functions . Ich habe den lag verwendet und lead Funktionen. Both gibt einen Wert aus einer Spalte aus einer Zeile zurück, die von der aktuellen Zeile versetzt ist. lag geht zurück und lead geht als nächstes in den Offset.

SELECT tokcat.text
FROM (
    SELECT text, category, chartype, lag(category,1) OVER w as previousCategory, lead(category,1) OVER w as nextCategory
    FROM token t, textBlockHasToken tb
    WHERE tb.tokenId = t.id
    WINDOW w AS (
        PARTITION BY textBlockId, sentence
        ORDER BY textBlockId, sentence, position
    )
) tokcat
WHERE 'NAME' = ANY(previousCategory)
AND 'NAME' = ANY(nextCategory)
AND 'NAME' <> ANY(category)

Vereinfachte Version:

SELECT text
FROM (
    SELECT text
          ,category 
          ,lag(category) OVER w as previous_cat
          ,lead(category) OVER w as next_cat
    FROM   token t
    JOIN   textblockhastoken tb ON tb.tokenid = t.id
    WINDOW w AS (PARTITION BY textblockid, sentence ORDER BY position)
    ) tokcat
WHERE  category <> 'NAME'
AND    previous_cat = 'NAME'
AND    next_cat = 'NAME';

Wichtige Punkte

  • = ANY() nicht benötigt wird, gibt die Fensterfunktion einen einzelnen Wert zurück
  • einige redundante Felder in der Unterabfrage
  • Sie müssen nicht nach Spalten ordnen, die Sie PARTITION BY verwenden - ORDER BY gilt innerhalb Partitionen
  • Verwenden Sie keine Groß-/Kleinschreibung ohne Anführungszeichen, das führt nur zu Verwirrung. (Noch besser:Verwenden Sie in PostgreSQL niemals Bezeichner mit gemischter Groß-/Kleinschreibung )