sql >> Databáze >  >> RDS >> PostgreSQL

Předejte funkci více sad nebo polí hodnot

Toho lze dosáhnout pomocí jednoduché funkce SQL. Klíčovou vlastností je funkce generate_subscripts() :

CREATE OR REPLACE FUNCTION f_attendance(_arr2d int[])
  RETURNS SETOF attendance AS
$func$
   SELECT a.*
   FROM   generate_subscripts($1, 1) i
   JOIN   attendance a ON a.class   = $1[i][1]
                      AND a.section = $1[i][2]
$func$  LANGUAGE ROWS 10 sql STABLE;

Volejte:

SELECT * FROM f_attendance(ARRAY[[1,1],[2,2]]);

Nebo totéž s polem literal - což je v některých kontextech výhodnější, zvláště u připravených příkazů:

SELECT * FROM f_attendance('{{1,1},{2,2}}');

Funkce vždy očekává 2D pole. I když minete jeden pár, vnořte jej:

SELECT * FROM f_attendance('{{1,1}}');

Audit vaší implementace

  1. Vytvořili jste funkci VOLATILE , ale může být STABLE . Podle dokumentace:

    Kvůli tomuto chování při vytváření snímků funkce obsahující pouze SELECT příkazy lze bezpečně označit jako STABLE .

    Související:

    • Jak předat parametr do funkce data
  2. Používáte také LANGUAGE plpgsql místo sql , což dává smysl, pokud funkci spustíte vícekrát ve stejné relaci. Ale pak to musíte také udělat STABLE nebo ztratíte potenciální výkonnostní přínos. Ještě jednou manuál:

    STABLE a IMMUTABLE funkce používají snímek vytvořený na začátku volajícího dotazu, zatímco VOLATILE funkce získávají čerstvý snímek na začátku každého dotazu, který provádějí.

  3. Váš EXPLAIN výstup zobrazuje Prohledávání pouze indexu , ne sekvenční skenování, jak předpokládáte ve svém komentáři.

  4. V EXPLAIN je také krok řazení výstup, který neodpovídá kódu, který ukazujete. Jste si jisti, že jste zkopírovali správný EXPLAIN? výstup? Jak jsi to vůbec získal? Funkce PL/pgSQL jsou černá políčka pro EXPLAIN . Použili jste auto_explain ? Podrobnosti:

    • Plán dotazů Postgres pro vyvolání UDF napsaný v pgpsql
  5. Plánovač dotazů Postgres netuší, kolik prvků pole bude mít předaný parametr, takže je těžké naplánovat dotaz a může se stát, že bude výchozí sekvenční skenování (v závislosti na více faktorech). Můžete si pomoci deklarováním očekávaného počtu řádků. Pokud obvykle nemáte více než 10 položek, přidejte ROWS 10 jako jsem to udělal teď výše. A znovu otestujte.



  1. Optimalizační prahy – seskupování a agregace dat, část 4

  2. Mysql počítá instance podřetězce a poté seřaďte podle

  3. MySQL - Výběr dat z více tabulek se stejnou strukturou, ale s různými daty

  4. 13 blogových článků o doporučených postupech a tipech pro návrh databáze