2016-03-21 5 views
0

Ich versuche, eine Funktion in Postgre Sql zu schreiben, um einen Durchschnitt über drei Spalten zu nehmen. Ich habe die folgende Funktion geschrieben:Erstellen Sie Funktion, um einen Durchschnitt von 3 Werten zu berechnen

create function xcol_avg (col1, col2, col3) 
returns numeric as $$ 

begin 

return (coalesce(col1, 0) + coalesce(col2,0) +coalesce(col3, 0))/ 
case when (col 1 is null or col1 = 0 then 0 else 1 end + 
case when (col 2 is null or col2 = 0 then 0 else 1 end + 
case when (col 3 is null or col3 = 0 then 0 else 1 end; 

end 

Was ist das Problem mit meinem Code? Gibt es auch eine Möglichkeit, die Funktion dazu zu bringen, null zurückzugeben, wenn sie durch 0 geteilt wird? Jede Hilfe wird wirklich geschätzt. Danke!

+0

Was genau ist Ihre Frage? –

+0

@Kristen, ich habe meine Antwort hinzugefügt. Hoffe, das gibt Ihnen genug Informationen zu diesem Thema. Sie haben verschiedene Probleme mit Ihrer Funktion. Ich schlage vor, Sie lesen das Handbuch: http://www.postgresql.org/docs/current/static/sql-createfunction.html –

Antwort

1

Tatsächlich können Sie eine Funktion erstellen, die eine variable Anzahl von Argumenten verwendet und abhängig von ihrer Anzahl den Durchschnitt berechnet. In Postgres gibt es ein Wort VARIADIC für solche Dinge:

SQL-Funktionen deklariert werden können variable Anzahl von Argumenten zu akzeptieren, solange alle „optional“ Argumente vom gleichen Datentyp sind

Funktionscode:

CREATE FUNCTION xcol_avg(numeric, VARIADIC numeric[]) 
    RETURNS numeric 
    LANGUAGE plpgsql 
    IMMUTABLE 
AS $$ 
BEGIN 
    RETURN (SELECT AVG(vals) FROM unnest($2 || ARRAY[$1]) t(vals)); 
END; 
$$; 

Anwendungsfall mit einer unterschiedlichen Anzahl von Argumenten:

select xcol_avg(1,6); -- returns 3.5 
select xcol_avg(1,5.5,4); -- returns 3.5 
select xcol_avg(1,2,3,4,5,6,7); -- returns 4 

Klicken Sie auf diese Button dieses Online zu versuchen.

Erläuterung:

  • eine Funktion als IMMUTABLE Kennzeichnung verbessert die Ausführungszeit, indem sie das Optimierungsprogramm die Funktion vorzunehmen auszuwerten. Unveränderliche Funktionen können die Datenbank nicht ändern und garantieren immer die gleichen Ergebnisse, wenn sie mit derselben Eingabe aufgerufen werden.
  • Wenn der letzte Parameter einer Funktion als VARIADIC angegeben wird, der vom Typ Array sein muss, können Sie optionale Argumente angeben, die an die Funktion als Array übergeben werden. Beachten Sie, dass Sie das Array nicht explizit schreiben, sondern nur Ihre Parameter wie gewohnt auflisten.
  • unnest() ist eine Funktion, die eine Reihe von Zeilen durch Erweitern eines Arrays zurückgibt. Mit anderen Worten, es "entpackt" die Array-Elemente in separate Zeilen.
  • || ist ein Array-Operator, der die Array-Array-Verkettung bereitstellt. Hier dient es dem Zweck, das erste (erforderliche) Argument mit dem Rest zu verbinden, der in einem VARIADIC Array angegeben ist.
  • AVG() ist eine Aggregatfunktion, die einen Durchschnitt aller Eingabewerte berechnet. In unserem Fall würde es "ausgepackte" Zeilen aus einer Spalte namens vals nehmen und den Durchschnitt berechnen.

Mit dieser Lösung, die Sie von Null, da mindestens ein Argument Sorgen machen müssen, um den Job nicht über Teilung erforderlich ist und avg() tut man manuell den Nenner durch den Aufbau tun wollte.

es in einer Abfrage Anwenden:

Diese Funktion wird auch für die Berechnung im Durchschnitt mehr Spalten in einer Zeile funktionieren würde.Betrachten Sie eine Tabelle tbl mit Spalten name, cost1, cost2, cost3 und unter Anweisung:

SELECT 
    name, cost1, cost2, cost3, 
    xcol_avg(cost1, cost2, cost3) AS average_cost 
FROM tbl 

Weitere allgemeine Informationen über CREATE FUNCTION Check the resourceful documentation.

Verwandte Themen