2015-08-13 7 views
2

Étant donné une table définie en tant que telle:PostgreSQL: Aplatir une relation avec un tableau émette une ligne par entrée du tableau

CREATE TABLE test_values(name TEXT, values INTEGER[]); 

... et les valeurs suivantes:

| name | values | 
+-------+---------+ 
| hello | {1,2,3} | 
| world | {4,5,6} | 

Je suis en essayant de trouver une requête qui retournera:

| name | value | 
+-------+-------+ 
| hello | 1  | 
| hello | 2  | 
| hello | 3  | 
| world | 4  | 
| world | 5  | 
| world | 6  | 

J'ai examiné the upstream documentation on accessing arrays, et a essayé de penser à ce qu'un solut ion en utilisant the unnest() function ressemblerait, mais ont été à venir vide.

Une solution idéale serait facile à utiliser même dans les cas où il y avait un nombre significatif de colonnes autres que le tableau en cours d'expansion et aucune clé primaire. La gestion d'un cas avec plusieurs tableaux n'est pas importante.

+1

N'a pas 'sélectionner le nom, unnest (valeurs) "valeur" de test_values;' travail? – bgoldst

Répondre

6

Vous peut mettre la fonction set-retour unnest() dans le SELECT liste like Raphaël suggests. Mais dans Postgres 9.3 ou plus tard, utilisez une jointure LATERAL à la place. Il est le plus propre, de préférence, manière conforme aux normes pour mettre mise en retour des fonctions dans la liste FROM, pas dans la liste SELECT:

SELECT name, value 
FROM tbl, unnest(values) value; -- implicit CROSS JOIN LATERAL 

Une différence subtile: cette chute lignes avec vide/NULL values du résultat puisque unnest() renvoie aucune ligne, tandis que le même est converti en une valeur NULL dans la liste FROM et renvoyé malgré tout. La requête équivalente à 100% est:

SELECT t.name, v.value 
FROM tbl t 
LEFT JOIN unnest(t.values) v(value) ON true; 
3

Eh bien, vous donner les données, la doc, alors ... nous allons le mélanger;)

select 
name, 
unnest(values) as value 
from test_values 

voir SqlFiddle

+1

C'est la partie où je me sens vraiment idiot. :) –

+0

@CharlesDuffy ou peut-être juste fatigué ... –

+0

Peu familier avec la sémantique de la sélection d'un tuple avec une séquence comme l'un de ses éléments, je peux plaider. Je l'accepterai quand le temps sera écoulé. –