Renvoie toutes les combinaisons possibles de valeurs sur les colonnes dans SQL

Comment puis-je retourner une liste de toutes les combinaisons de valeurs dans 2 colonnes afin qu'elles soient de nouvelles lignes dans T-SQL?

Par exemple

Col1, Col2
----  ----
1     2
1     4
1     5

Et transformez ceci en toutes les combinaisons:

1     2
1     4
1     5
2     4
2     5
4     5
25
demandé sur ItamarG3 2010-12-07 19:01:04

8 réponses

En supposant au moins SQL 2005 pour le CTE :

;with cteAllColumns as (
    select col1 as col
        from YourTable
    union
    select col2 as col
        from YourTable
)
select c1.col, c2.col 
    from cteAllColumns c1 
        cross join cteAllColumns c2 
    where c1.col < c2.col
    order by c1.col, c2.col
31
répondu Joe Stefanelli 2010-12-07 16:14:25

Vous pouvez cartésien joindre la table à elle-même, ce qui retournerait toutes les combinaisons des deux colonnes.

select 
    distinct
    t1.Col1,
    t2.Col2
from 
    MyTable t1,
    MyTable t2
27
répondu Bob Black 2010-12-07 16:18:59

Vous pouvez faire une jointure auto-croisée...

SELECT a.Col1, b.Col2
FROM MyTable a
CROSS JOIN MyTable b
9
répondu JNK 2010-12-07 16:09:56

Je cherchais quelque chose qui le ferait en utilisant uniquement le SQL disponible pour Microsoft Access 2016. J'ai fini par trouver quelque chose que d'autres peuvent trouver utile. Ce code utilise la jointure croisée, donc j'ai trouvé qu'il est nécessaire de diviser les deux colonnes en deux tables séparées (chacune avec une colonne). L'instruction et force une colonne à être inférieure à l'autre, éliminant ainsi toute sorte d'occurrences répétitives 1-2, 2-1.

SELECT DISTINCT Table1.Column1, Table2.Column1
FROM Table1, Table2
WHERE Table1.Column1 <> Table2.Column1
AND Table2.Column1 < Table1.Column1;
5
répondu Josh 2017-05-31 18:28:48

Je pense que cela a été trop compliqué!

Juste:

SELECT distinct Col1, Col2

FROM MyTable

Pour obtenir toutes les combinaisons possibles..

2
répondu Casual user 2017-02-28 11:31:50

Cela utilise 2 cte, le premier reproduit simplement votre table d'entrée, le second transforme les deux colonnes en une seule colonne. La sélection finale crossjoin est définie sur elle-même pour produire la sortie requise

with t(c1,c2)
AS
(
    select 1,2
    union select 1,4
    union select 1,5
)
,t2(c)
as
(
    select c1 from t
    union select c2 from t
)
select t2_1.c, t2_2.c
from t2 t2_1 
cross join t2 t2_2
where t2_1.c<t2_2.c
order by t2_1.c
1
répondu Jamiec 2010-12-07 16:23:27

Je trouve une jointure intérieure plus intuitive car je l'utilise plus fréquemment qu'une jointure croisée:

;with cteAllColumns as (
select col1 as col
    from YourTable
union
select col2 as col
    from YourTable
) 

select c1.col, c2.col 
from cteAllColumns c1 
    join cteAllColumns c2 on 1=1
where c1.col < c2.col
order by c1.col, c2.col
0
répondu Tim Hauser 2015-06-25 21:58:06

Faciliter la réponse de Joe

declare @t1 table  (col1 varchar(5))
insert @t1 
    select 'A' UNION
    select 'B' UNION
    select 'C' 


declare @t2 table  (col2 varchar(5))
insert @t2
    select '1' UNION
    select '2' UNION
    select '3' 


;with cteAllColumns as (
    select col1 as col
        from @t1
    union
    select col2 as col
        from @t2
)
select c1.col, c2.col 
    from cteAllColumns c1 
        cross join cteAllColumns c2 
    where c1.col < c2.col
    order by c1.col, c2.col

Vérifiez votre quantité de combinaisons (nombre de lignes) http://www.calculatorsoup.com/calculators/discretemathematics/combinations.php

0
répondu Faheem Ahmad 2017-01-11 22:27:28