1

是否可以从没有任何共同结果的表或视图中进行 UNION 查询?我正在尝试做的是将来自不同视图的数据组合成一个结果。我有

select a,b,null,c from VIEW1, VIEW2 where VIEW1.a = VIEW2.a
UNION
select null,null,z,null from VIEW3

我希望结果是 a,b,z,c。这是我会使用 select from 的地方吗?那看起来像什么?

select ? from (
select a,b,null,c from VIEW1, VIEW2 where VIEW1.a = VIEW2.a
UNION
select null,null,z,null from VIEW3)

我正在使用 MS SQL Server,并且视图没有主键。非常感谢。

4

7 回答 7

2

如果我理解你的问题,你可能会得到这样的结果:

a1, b1, null, c1
a2, b2, null, c2
a3, b2, null, c3
null, null, z1, null
null, null, z2, null
null, null, z3, nul

l

..但你想要得到的是这样的结果:

a1, b1, z1, c1
a2, b2, z2, c2
a3, b2, z3, c3

我是否正确理解了问题?

如果这是正确的,您将需要有一种方法将这些子查询连接在一起,以便您可以告诉 SQL 1 一起运行,2 一起运行,等等。

于 2009-05-19T21:08:01.917 回答
2

联合连接结果集,它不组合它们。

因此,您将从第一个查询中得到的是:

  a      b    (null)  c
(null) (null)   z    (null)

如果你想组合它们,你必须加入它们,然后你需要有一些共同点,或者你必须在程序中组合数据。

每个人只有 1 行吗?

如果是这样,那么如果上面的模式总是这样,这将起作用:

SELECT SQ1.a, SQ1.b, SQ2.z, SQ1.c
FROM (
    SELECT 1 k, View1.a, b, NULL z, c
    FROM View1 INNER JOIN View2 ON View1.a = View2.a) SQ1
INNER JOIN (
    SELECT 1 k, NULL a, NULL b, z, NULL c
    FROM View3) SQ2 ON SQ1.k = SQ2.k

但是,如果您不知道 View3.a 是否有值或 View1.a 是否有值,并且如果有值 3,您想要第一个查询中的值,那么这将起作用:

SELECT COALESCE(SQ1.a, SQ2.a) a, COALESCE(SQ1.b, SQ2.b) b,
    COALESCE(SQ1.z, SQ2.z) z, COALESCE(SQ1.c, SQ2.c) c
FROM (
    SELECT 1 k, View1.a, b, NULL z, c
    FROM View1 INNER JOIN View2 ON View1.a = View2.a) SQ1
INNER JOIN (
    SELECT 1 k, NULL a, NULL b, z, NULL c
    FROM View3) SQ2 ON SQ1.k = SQ2.k

但是,这里有一个很大的 BUT。如果您在任一视图中都有不止一行,那么您最终将得到不属于一起的数据。在这种情况下,你们一定有共同点。

这是我尝试的完整代码以及结果:

USE master
GO

DROP DATABASE TestDB
GO

CREATE DATABASE TestDB
GO

USE TestDB
GO

CREATE TABLE View1
(
    a INT,
    b INT,
    c INT
)
GO

CREATE TABLE View2
(
    a INT,
    z INT
)
GO

CREATE TABLE View3
(
    z INT
)
GO

INSERT INTO View1 (a, b, c) VALUES (10, 20, 30)
GO

INSERT INTO View2 (a, z) VALUES (10, 40)
GO

INSERT INTO View3 (z) VALUES (50)
GO


SELECT View1.a, b, NULL z, c
FROM View1 INNER JOIN View2 ON View1.a = View2.a
UNION
SELECT NULL a, NULL b, z, NULL c
FROM View3

SELECT SQ1.a, SQ1.b, SQ2.z, SQ1.c
FROM (
    SELECT 1 k, View1.a, b, NULL z, c
    FROM View1 INNER JOIN View2 ON View1.a = View2.a) SQ1
INNER JOIN (
    SELECT 1 k, NULL a, NULL b, z, NULL c
    FROM View3) SQ2 ON SQ1.k = SQ2.k

SELECT COALESCE(SQ1.a, SQ2.a) a, COALESCE(SQ1.b, SQ2.b) b,
    COALESCE(SQ1.z, SQ2.z) z, COALESCE(SQ1.c, SQ2.c) c
FROM (
    SELECT 1 k, View1.a, b, NULL z, c
    FROM View1 INNER JOIN View2 ON View1.a = View2.a) SQ1
INNER JOIN (
    SELECT 1 k, NULL a, NULL b, z, NULL c
    FROM View3) SQ2 ON SQ1.k = SQ2.k

结果:

a           b           z           c
----------- ----------- ----------- -----------
NULL        NULL        50          NULL
10          20          NULL        30

(2 row(s) affected)

a           b           z           c
----------- ----------- ----------- -----------
10          20          50          30

(1 row(s) affected)

a           b           z           c
----------- ----------- ----------- -----------
10          20          50          30

(1 row(s) affected)

如果向 View3 添加一行,如下所示:

INSERT INTO View3 (z) VALUES (51)

然后你会得到这些结果,注意加倍的行:

a           b           z           c
----------- ----------- ----------- -----------
NULL        NULL        50          NULL
NULL        NULL        51          NULL
10          20          NULL        30

(3 row(s) affected)

a           b           z           c
----------- ----------- ----------- -----------
10          20          50          30
10          20          51          30

(2 row(s) affected)

a           b           z           c
----------- ----------- ----------- -----------
10          20          50          30
10          20          51          30

(2 row(s) affected)
于 2009-05-19T21:08:17.423 回答
1

如果我理解这一点:您是否试图“折叠”您的结果并摆脱所有 NULL?如果是这样,view3 的结果是否会对应于 view1/view2 的结果?如果有,是什么关系?如果不是,结果的数量是否至少匹配?

于 2009-05-19T21:05:40.283 回答
1


对于多条记录,ROW_NUMBER() 方法对我有用。Select 1 k 方法返回笛卡尔积。

SELECT SQ1.a, SQ1.b, SQ2.z, SQ1.c
FROM (
    SELECT ROW_NUMBER() OVER (ORDER BY a) k, View1.a, b, NULL z, c
    FROM View1 INNER JOIN View2 ON View1.a = View2.a) SQ1
INNER JOIN (
    SELECT ROW_NUMBER() OVER (ORDER BY b) k, NULL a, NULL b, z, NULL c
    FROM View3) SQ2 ON SQ1.k = SQ2.k
于 2016-10-08T18:38:43.377 回答
0

难道你正在寻找这样的东西吗?(只是一个疯狂的猜测)

SELECT 
  VIEW1.a,
  VIEW1.b,
  (SELECT TOP 1 z FROM VIEW3) AS z,
  VIEW2.c
FROM
  VIEW1, VIEW2 
WHERE
  VIEW1.a = VIEW2.a
于 2009-05-19T21:07:04.430 回答
0

任何 sql 选择(包括联合)的结果都是一组静态列。(没有多态性。)

但是您不必使用每一行中的所有列,您可以在该列没有值的行中使用空值。我还建议您包含一个“类型”行,以便客户端可以告诉给定行的类型(和有趣的列)。

例子:

 (Select
   'room' as view_type
 , rooms.room as room
 , NULL as color
 From rooms 
 )
UNION ALL
(Select
  'color' as view_type
 , NULL as room
 , colors.color as color
 From colors 
)
于 2009-05-19T21:11:17.057 回答
0

你实际上想要一个交叉连接:

选择 v1.a,v1.b,VIEW3.z,v1.c from (SELECT a,b,c, FROM VIEW1, VIEW2 where VIEW1.a = VIEW2.a) as v1 CROSS JOIN VIEW3

于 2009-05-19T21:22:06.973 回答