我有以下表格
表1
ID1 YEAR1
1 1980
2 1964
3 1910
表2
ID2 YEAR2 VALUE
1 2000 A
1 1900 B
2 1950 C
2 1900 B
3 2000 C
3 1970 B
4 1900 D
4 1800 E
我想加入/查询这些表格:
对于表1中的每个ID1匹配,添加一个名为VALUE的列 - 因此列名称将为A,B,......等等,该列将为TRUE(T)或FALSE(F)。
如果ID1与表2中的ID2匹配,则列A ...将为TRUE,而表2中与ID2匹配的给定行的YEAR2小于表1中给定1的值YEAR1和VALUE从表2中具有ID2的行得到A
所以结果表如下:
ID1 YEAR1 A B C D E
1 1980 F T F F F
2 1964 F T T F F
3 1910 F F F F F
答案 0 :(得分:1)
您可以使用如下查询:
SELECT t1.ID1, t1.YEAR1,
COUNT(CASE WHEN t2.VALUE = 'A' AND t1.YEAR1 > t2.YEAR2 THEN 1 END) AS A,
COUNT(CASE WHEN t2.VALUE = 'B' AND t1.YEAR1 > t2.YEAR2 THEN 1 END) AS B,
COUNT(CASE WHEN t2.VALUE = 'C' AND t1.YEAR1 > t2.YEAR2 THEN 1 END) AS C,
COUNT(CASE WHEN t2.VALUE = 'D' AND t1.YEAR1 > t2.YEAR2 THEN 1 END) AS D,
COUNT(CASE WHEN t2.VALUE = 'E' AND t1.YEAR1 > t2.YEAR2 THEN 1 END) AS E,
COUNT(CASE WHEN t2.VALUE = 'F' AND t1.YEAR1 > t2.YEAR2 THEN 1 END) AS F
FROM Table1 AS t1
LEFT JOIN Table2 AS t2 ON t1.ID1 = t2.ID2
GROUP BY t1.ID1, t1.YEAR1
如果,例如列A
的值为1
,然后将其视为T
,否则将其视为F
。
答案 1 :(得分:0)
你可以使用group by Giorgos或像这样加入:
SELECT T1.ID1, T1.YEAR1
FROM TABLE1 T1
LEFT JOIN TABLE2 A ON T1.ID1 =SELECT T1.ID1, T1.YEAR1,
CASE WHEN A.ID2 IS NOT NULL THEN 'T' ELSE 'F' END AS A,
CASE WHEN B.ID2 IS NOT NULL THEN 'T' ELSE 'F' END AS B,
CASE WHEN C.ID2 IS NOT NULL THEN 'T' ELSE 'F' END AS C,
CASE WHEN D.ID2 IS NOT NULL THEN 'T' ELSE 'F' END AS D,
CASE WHEN E.ID2 IS NOT NULL THEN 'T' ELSE 'F' END AS E
FROM TABLE1 T1
LEFT JOIN TABLE2 A ON T1.ID1 = A.ID2 AND T1.YEAR1 > A.YEAR2 AND A.VALUE = 'A'
LEFT JOIN TABLE2 B ON T1.ID1 = B.ID2 AND T1.YEAR1 > B.YEAR2 AND B.VALUE = 'B'
LEFT JOIN TABLE2 C ON T1.ID1 = C.ID2 AND T1.YEAR1 > C.YEAR2 AND C.VALUE = 'C'
LEFT JOIN TABLE2 D ON T1.ID1 = D.ID2 AND T1.YEAR1 > D.YEAR2 AND D.VALUE = 'D'
LEFT JOIN TABLE2 E ON T1.ID1 = E.ID2 AND T1.YEAR1 > E.YEAR2 AND E.VALUE = 'E'
答案 2 :(得分:0)
我只想使用条件聚合和布尔类型:
SELECT t1.id1,
BOOL_OR( (t2.VALUE = 'A' AND t2.YEAR < t1.YEAR) ) as A,
BOOL_OR( (t2.VALUE = 'B' AND t2.YEAR < t1.YEAR) ) as B,
BOOL_OR( (t2.VALUE = 'C' AND t2.YEAR < t1.YEAR) ) as C,
BOOL_OR( (t2.VALUE = 'D' AND t2.YEAR < t1.YEAR) ) as D,
BOOL_OR( (t2.VALUE = 'E' AND t2.YEAR < t1.YEAR) ) as E,
BOOL_OR( (t2.VALUE = 'F' AND t2.YEAR < t1.YEAR) ) as F
FROM Table1 t1 LEFT JOIN
Table2 t2
ON t1.ID1 = t2.ID2
GROUP BY t1.ID1;
答案 3 :(得分:0)
您已将问题标记为postgresql
,因此我将使用common table expressions和tablefunc extension.
这实际上是在数据透视表的帮助下最佳表达的问题的典型示例。
如您所见,最乏味的部分是填充虚拟对象的空位。
CREATE EXTENSION tablefunc; -- If you haven’t already
WITH ct AS (
SELECT * FROM CROSSTAB (
'SELECT id2, t1.year1, t2.value, t2.year2 < t1.year1
FROM t2 JOIN t1 ON t1.id1 = t2.id2 ORDER BY 1,3',
$$VALUES('A'::CHAR(1)),('B'),('C'),('D'),('E')$$)
AS ct("ID1" INT, "YEAR1" INT,
"A" BOOL, "B" BOOL, "C" BOOL, "D" BOOL, "E" BOOL)
) SELECT "ID1", "YEAR1",
("A" AND ("A" IS NOT NULL)) AS "A",
("B" AND ("B" IS NOT NULL)) AS "B",
("C" AND ("C" IS NOT NULL)) AS "C",
("D" AND ("D" IS NOT NULL)) AS "D",
("E" AND ("E" IS NOT NULL)) AS "E",
FROM ct;