2011-09-27 8 views
10

Sono nuovo di PostgreSQL.Come fare pivoting in PostgreSQL

Supponiamo che io ho una tabella come sotto

colorname Hexa rgb rgbvalue 
Violet #8B00FF r 139 
Violet #8B00FF g 0 
Violet #8B00FF b 255 
Indigo #4B0082 r 75 
Indigo #4B0082 g 0 
Indigo #4B0082 b 130 
Blue #0000FF r 0 
Blue #0000FF g 0 
Blue #0000FF b 255 

Se faccio un pivot in SQL Server come

SELECT colorname,hexa,[r], [g], [b] 
FROM 
(SELECT colorname,hexa,rgb,rgbvalue 
    FROM tblPivot) AS TableToBePivoted 
PIVOT 
(
sum(rgbvalue) 
FOR rgb IN ([r], [g], [b]) 
) AS PivotedTable; 

ho l'uscita come

colorname hexa r g b 
Blue #0000FF 0 0 255 
Indigo #4B0082 75 0 130 
Violet #8B00FF 139 0 255 

Come fare il lo stesso usando PostgreSQL?

Il mio tentativo è

SELECT * 
FROM crosstab 
(
    'SELECT 
     colorname 
     ,hexa 
     ,rgb 
     ,rgbvalue 
    FROM tblPivot' 
)AS ct(colorname text, hexa text, rgb text, rgbvalue int); 

Ma geting errore:

ERROR: function crosstab(unknown) does not exist 
LINE 2: FROM crosstab 
      ^
HINT: No function matches the given name and argument types. You might need to add explicit type casts. 
********** Error ********** 
ERROR: function crosstab(unknown) does not exist** 

C'è un modo elegante di farlo in PostgreSQL (qualsiasi Costruito nella funzione ...) Qual è la prassi standard così facendo ?

risposta

5

Questo può essere espresso come un JOIN:

SELECT c.colorname, c.hexa, r.rgbvalue, g.rgbvalue, b.rgbvalue 
FROM (SELECT colorname, hexa 
     FROM sometable 
     GROUP BY colorname) c 
JOIN sometable r ON c.colorname = r.colorname AND r.rgb = 'r' 
JOIN sometable g ON c.colorname = g.colorname AND g.rgb = 'g' 
JOIN sometable b ON c.colorname = b.colorname AND b.rgb = 'b' 
; 
+0

Ma perché a campi incrociati didnot lavoro ... non che non supporta in la versione corrente che sto usando? –

+4

'crosstab()' appartiene al modulo 'tablefunc'. Dovrai abilitarlo usando 'CREATE EXTENSION'. Detto ciò; la convenienza che offre potrebbe non essere così eccezionale; postgresql è straordinariamente bravo a ottimizzare i join, e questo tipo di codice sarà più riconoscibile su più database e più sviluppatori. – SingleNegationElimination

+0

Se fai un sacco di roba crosstab, il modulo contrib di tablefunc può essere ottimo. Se sei su Ubuntu, puoi aggiungere le funzioni tablefunc a un db facendo ciò: psql dbname -f /usr/share/postgresql/8.4/contrib/tablefunc.sql o qualcosa di simile. –

32

Esegui questo

CREATE EXTENSION tablefunc; 

e tenta di eseguire la query

+2

se lo eseguo, ricevo "ERRORE: estensione" tablefunc "già esiste" ma quando provo ad usarlo viene visualizzato "ERRORE: la funzione crosstab (sconosciuta) non esiste". Sto usando Postgres 9.2.1 su Mac 10.9.2. Qualche idea? – Black

+2

Assicurati di essere connesso al tuo database con \ c nome_db e poi esegui il comando sopra. – sm0ke21

+1

Questa [risposta] (https://stackoverflow.com/a/23073241/177116) ha risposto alla domanda sollevata nel commento di @ Black. –