据我所知,我有一个非规范化的表。以下是一些表格列表:
... C, F, T, C1, F1, T1, .... C8, T8, F8.....
是否可以在行中选择这些值?
这样的事情:
C, F, T
C1, F1, T1
......
C8, F8, T8
答案 0 :(得分:4)
您可以使用union all
:
select C, F, T from table t
union all
select C1, F1, T1 from table t
union all
. . .
select C8, F8, T8 from table t;
请注意使用union all
代替union
。 union
执行自动重复删除,因此您可能无法使用union
获取所有值(以及操作更昂贵)。
这通常会导致表格被扫描9次。如果你有一个大表,还有其他方法可能更有效。
编辑:
更有效的方法可能是cross join
和case
。在DB2中,我认为这将是:
select (case n.n when 0 then C
when 1 then C1
. . .
when 8 then C8
end) as C,
(case n.n when 0 then F
when 1 then F1
. . .
when 8 then F8
end) as F,
(case n.n when 0 then T
when 1 then T1
. . .
when 8 then T8
end) as T
from table t cross join
(select 0 as n from sysibm.sysdummy1 union all select 1 from sysibm.sysdummy1 union all . . .
select 9 from sysibm.sysdummy1
) n;
这可能看起来更多,但它应该只读取更大的表一次,其余的工作是内存操作。
答案 1 :(得分:1)
select c,f,t from table
union all
select c1,f1,t1 from table
union all
select c8,f8,t8 from table
确保按每个SELECT语句的WHERE子句进行过滤。
答案 2 :(得分:0)
类似于Gordons的一个技巧是使用LATERAL
来避免多次扫描:
with t(c1,t1,f1,c2,t2,f2) as ( values (1,2,3,4,5,6) )
select y.c, y.t, y.f
from t x
cross join lateral ( values (x.c1, x.t1, x.f1)
, (x.c2, x.t2, x.f2) ) y(c,t,f)
C T F
----------- ----------- -----------
1 2 3
4 5 6