Ici, #tmporigin
fait référence à votre requête originale qui produit les données de la question. Il suffit de remplacer le nom de la table par une sous-requête.
insert into resulttable
select
o.id,
case a.n when 1 then b1 when 2 then b2 else b3 end,
case a.n when 1 then c when 2 then e else g end
from #tmporigin o
cross join (select 1n union all select 2 union all select 3) a
La réponse originale ci-dessous, qui utilise la CTE et l'union, nécessite une évaluation de la CTE à trois reprises.
J'ai les résultats suivants provenant de plusieurs tables
Configurez donc cette requête en tant qu'expression de table commune.
;WITH CTE AS (
-- the query that produces that output
)
select id,b1,c from CTE
union all
select id,b2,e from CTE
union all
select id,b3,g from CTE
NOTE - Contrairement à la croyance populaire, votre CTE, bien qu'écrit une seule fois, est exécuté. trois fois dans la requête ci-dessus, une fois pour chacune des parties de l'union.
NOTE AUSSI que si l'on nomme 3 colonnes "b" (littéralement), il n'y a aucun moyen d'identifier laquelle est "b". b
En fait, SQL Server ne vous permettra pas d'utiliser la requête dans un CTE ou une sous-requête.
L'exemple suivant montre comment effectuer ce qui précède et révèle (si vous montrez le plan d'exécution) que l'ETC est exécuté trois fois ! (les lignes entre --- BELOW HERE
et --- ABOVE HERE
est un simulacre de la original query
qui produit le résultat indiqué dans la question.
if object_id('tempdb..#eav') is not null drop table #eav
;
create table #eav (id char(3), b int, v int)
insert #eav select 'abc', 2, 123
insert #eav select 'abc', 3, 321
insert #eav select 'abc', 7, 876
insert #eav select 'abd', 2, 456
insert #eav select 'abd', 3, 452
insert #eav select 'abd', 7, 234
insert #eav select 'abe', 2, 0
insert #eav select 'abe', 3, 123
insert #eav select 'abe', 7, 121
insert #eav select 'abf', 3, 535
insert #eav select 'abf', 7, 1212
;with cte as (
---- BELOW HERE
select id.id, b1, b1.v c, b2, b2.v e, b3, b3.v g
from
(select distinct id, 2 as b1, 3 as b2, 7 as b3 from #eav) id
left join #eav b1 on b1.b=id.b1 and b1.id=id.id
left join #eav b2 on b2.b=id.b2 and b2.id=id.id
left join #eav b3 on b3.b=id.b3 and b3.id=id.id
---- ABOVE HERE
)
select b1, c from cte
union all
select b2, e from cte
union all
select b3, g from cte
order by b1
Il est préférable de stocker les données dans une table temporaire avant de procéder à l'opération union all
sélectionner.