根据SQLServer

时间:2016-07-22 16:37:17

标签: sql-server

我有两个表(每个表有大约20列),没有列名匹配,但1列中的某些值与另一列中的值匹配(见下文)。

我希望根据主表中列中的True / False值得到某些列上的2个表的组合。

我正在使用Oracle SQL Developer中的SQLServer第三方JDBC驱动程序来完成所有这些工作(我不确定它是否或如何对我的语法产生影响)。

我确信这很简单,但我找不到任何执行此操作的示例,而且我对SQL太过新,无法理解它。

CREATE TABLE [dbo].[TableA] (
    [colA1]  VARCHAR (10) NULL,
    [colA2]  VARCHAR (10) NULL,
    [colA3]  VARCHAR (10) NULL,
    [colA4]  VARCHAR (10) NULL,
    [colA5]  VARCHAR (10) NULL,
    [colA6]  INT         NULL,
    [colKey] INT         NOT NULL,
    CONSTRAINT [PK_TableA] PRIMARY KEY CLUSTERED ([colKey] ASC)
);

CREATE TABLE [dbo].[TableB] (
    [colB1]  VARCHAR (10) NULL,
    [colB2]  VARCHAR (10) NULL,
    [colB3]  VARCHAR (10) NULL,
    [colB4]  INT         NULL,
    [colKey] INT         NOT NULL,
    PRIMARY KEY CLUSTERED ([colKey] ASC)
);

INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (1,'AC1-1','AC2-1','AC3-1',NULL,'FALSE',2016);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (2,'AC1-2','AC2-2','AC3-2',NULL,'FALSE',2016);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (3,'AC1-3',NULL,NULL,'AC4-3','TRUE',2016);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (4,'AC1-4',NULL,NULL,'AC4-4','TRUE',2016);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (5,'AC1-5','AC2-5','AC3-5',NULL,'FALSE',2015);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (6,'AC1-6','AC2-6','AC3-6',NULL,'FALSE',2015);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (7,'AC1-7',NULL,NULL,'AC4-7','TRUE',2015);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (8,'AC1-8',NULL,NULL,'AC4-8','TRUE',2015);
INSERT INTO TableA(colKey,colA1,colA2,colA3,colA4,colA5,colA6) VALUES (9,'AC1-9',NULL,NULL,'AC4-9','TRUE',2016);

INSERT INTO TableB(colKey,colB1,colB2,colB3,colB4) VALUES (1,'AC4-3','BC2-1','BC3-1',2015);
INSERT INTO TableB(colKey,colB1,colB2,colB3,colB4) VALUES (2,'AC4-4','BC2-2','BC3-2',2015);
INSERT INTO TableB(colKey,colB1,colB2,colB3,colB4) VALUES (3,'AC4-4','BC2-3','BC3-3',2016);
INSERT INTO TableB(colKey,colB1,colB2,colB3,colB4) VALUES (4,'AC4-3','BC2-4','BC3-4',2016);
INSERT INTO TableB(colKey,colB1,colB2,colB3,colB4) VALUES (5,'AC4-7','BC2-5','BC3-5',2015);
INSERT INTO TableB(colKey,colB1,colB2,colB3,colB4) VALUES (6,'AC4-8','BC2-6','BC3-6',2015);

TableA              
+-------+--------+--------+--------+-------+-------+
| colA1 | colA2  | colA3  | colA4  | colA5 | colA6 |
+-------+--------+--------+--------+-------+-------+
| AC1-1 | AC2-1  | AC3-1  | (Null) | FALSE |  2016 |
| AC1-2 | AC2-2  | AC3-2  | (Null) | FALSE |  2016 |
| AC1-3 | (Null) | (Null) | AC4-3  | TRUE  |  2016 |
| AC1-4 | (Null) | (Null) | AC4-4  | TRUE  |  2016 |
| AC1-5 | AC2-5  | AC3-5  | (Null) | FALSE |  2015 |
| AC1-6 | AC2-6  | AC3-6  | (Null) | FALSE |  2015 |
| AC1-7 | (Null) | (Null) | AC4-7  | TRUE  |  2015 |
| AC1-8 | (Null) | (Null) | AC4-8  | TRUE  |  2015 |
| AC1-9 | (Null) | (Null) | AC4-9  | TRUE  |  2016 |
+-------+--------+--------+--------+-------+-------+

TableB      
+-------+-------+-------+-------+
| colB1 | colB2 | colB3 | colB4 |
+-------+-------+-------+-------+
| AC4-3 | BC2-1 | BC3-1 |  2015 |
| AC4-4 | BC2-2 | BC3-2 |  2015 |
| AC4-4 | BC2-3 | BC3-3 |  2016 |
| AC4-3 | BC2-4 | BC3-4 |  2016 |
+-------+-------+-------+-------+

Results Table           
+-------+--------+-------+-------------------------+-------------------------+
| colA1 | colA4  | colA5 | combined(colA2 & colB2) | combined(colA3 & colB3) |
+-------+--------+-------+-------------------------+-------------------------+
| AC1-1 | (null) | FALSE | AC2-1                   | AC3-1                   |
| AC1-2 | (null) | FALSE | AC2-2                   | AC3-2                   |
| AC1-3 | AC4-3  | TRUE  | BC2-1                   | BC3-1                   |
| AC1-4 | AC4-4  | TRUE  | BC2-2                   | BC3-2                   |
| AC1-9 | AC4-9  | TRUE  | (null)                  | (null)                  |
+-------+--------+-------+-------------------------+-------------------------+

所以我觉得我需要这样的SELECT:

SELECT colA1, colA5, 
IF colA5 = True
    THEN colB2, colB3, etc.
    ELSE colA2, ColA3, etc.
FROM tableB, tableA
WHERE colA1 = colB1 AND colB4 = 2016 AND colA6 = 2016

我试过这个:

SELECT A.colA1
,A.colA4
,A.colA5
,CASE 
    WHEN A.colA5 = TRUE
        THEN B.colB2
    ELSE A.colA2
    END AS 'combined(colA2 & colB2)'
,CASE 
    WHEN A.colA5 = TRUE
        THEN B.colB3
    ELSE A.colA4
    END AS 'combined(colA3 & colB3)'
,
FROM TableA A
    ,TableB B
WHERE A.colA6 = '2016'
    AND B.colB4 = '2016'
    AND (
        A.colA4 = B.colB1
        OR A.colA4 IS NULL
        )

我得到的是:

+-------+-------+-------+-------------------------+-------------------------+
| colA1 | colA4 | colA5 | combined(colA2 & colB2) | combined(colA3 & colB3) |
+-------+-------+-------+-------------------------+-------------------------+
| AC1-3 | AC4-3 | TRUE  | BC2-1                   | BC3-1                   |
| AC1-4 | AC4-4 | TRUE  | BC2-2                   | BC3-2                   |
+-------+-------+-------+-------------------------+-------------------------+

所以我错过了TableA / colA5为FALSE的行。此外,我需要其中12个"合并"列,有没有办法可以避免使用12个CASE语句?

1 个答案:

答案 0 :(得分:0)

在了解了连接和案例后,这里是答案(虽然显然我将不得不使用我希望避免的12个CASE语句。)

SELECT A.colA1
,A.colA4
,A.colA5
,CASE 
    WHEN A.colA5 = 'TRUE'
        THEN B.colB2
        ELSE A.colA2
    END AS 'combined(colA2 & colB2)'
,CASE 
    WHEN A.colA5 = 'TRUE'
        THEN B.colB3
        ELSE A.colA3
    END AS 'combined(colA3 & colB3)'
FROM TableA A LEFT JOIN TableB B ON A.colA4 = B.colB1
WHERE (A.colA6 = '2016' and A.colA5 ='FALSE')
    or (A.colA6 = '2016' and A.colA5 ='true' and B.colB4 = '2016')
    or (A.colA6 = '2016' and A.colA5 ='true' and B.colB4 is null)
    ;