繁体   English   中英

在一个 SQL 语句中组合多个连接

[英]combining multiple joins in one SQL statement

我的数据库架构中有三个表:MY_TABLE、CREATIVE_SIZE、REVERSE_CREATIVE_SIZE

MY_TABLE由三列组成

|            NAME             |   BANNER_W  |  BANNER_H |
|     320x480_Toyota          |     320     |   480     |
| Tim_Horton_IO00122_1024x320 |     1024    |   320     |
|     Walmart_IO00134         |     80      |    80     |
|     Mcdonalds_320x1024      |     320     |   1024    |
....

CREATIVE_SIZE_TABLE由一列组成

| CREATIVE_SIZE |
|   320x480     |
|   1024x320    |
....

REVERSE_CREATIVE_SIZE_TABLE由两列组成

| CREATIVE_SIZE | REVERSED_SIZE |
|   320x480     | 480x320       |     
|   1024x320    | 320x1024      |
....

我有几个条件要实现:

  1. FULL OUTER JOIN MY_TABLE 和 CREATIVE_SIZE_TABLE ON NAME包含CREATIVE_SIZE

  2. 因为它是完全外连接,所以一些 CREATIVE_SIZE 是 NULL,对于那些 NULL 值,我想做两件事:

    一个。 检查他们的 NAME 是否包含 REVERSED_SIZE,如果包含,则使用 CREATIVE_SIZE 填充 NULL

    湾。 用 BANNER_W 和 BANNER_H 填充 NULL 的 rest(采用 aaaxbbb 格式)

到目前为止我只有这个,我不知道如何添加a. b. 在我的 sql 声明中:

SELECT CREATIVE_NAME, AD_BANNER_W, AD_BANNER_H, CREATIVE_SIZE
FROM CREATIVE_SIZE_TABLE cst
    LEFT JOIN CREATIVE_SIZE cs
    ON cst.CREATIVE_NAME ILIKE '%' || cs.CREATIVE_SIZE || '%'

任何帮助表示赞赏。 谢谢。

只需使用左连接,然后合并即可找到非 null 之一。

SELECT COALESCE(cs.CREATIVE_SIZE, revs.REVERSED_SIZE, AD_BANNER_W||'x'||AD_BANNER_H) as MYSIZE,
   CREATIVE_NAME, AD_BANNER_W, AD_BANNER_H, CREATIVE_SIZE
FROM CREATIVE_SIZE_TABLE cst
LEFT JOIN CREATIVE_SIZE cs
    ON cst.CREATIVE_NAME ILIKE '%' || cs.CREATIVE_SIZE || '%'
LEFT JOIN REVERSE_CREATIVE_SIZE_TABLE revs
    ON cst.CREATIVE_NAME ILIKE '%' || revs.REVERSED_SIZE || '%'

注意:虽然这会起作用,但 LIKE 总是很慢——如果你经常这样做,你可能想要对数据进行一些预处理以加快查询速度——如果这是一次性的,那么它不会事情。

与 Hogan 发布的代码相同,但使用 CONTAINS 来避免 WHERE 子句中的字符串操作

WITH my_table AS (            
    SELECT * FROM VALUES 
       ('320x480_Toyota', 320, 480)
      ,('Tim_Horton_IO00122_1024x320', 1024, 320)
      ,('Walmart_IO00134', 80,  80)
      ,('Mcdonalds_320x1024', 320, 1024)
    v(name, banner_w, banner_h)
), creative_size_table AS (
    SELECT * FROM VALUES
    ('320x480' ),
    ('1024x320')
    v(creative_size )
), reverse_creative_size_table AS (
    SELECT * FROM VALUES 
    ('320x480', '480x320' ),
    ('1024x320', '320x1024' )
    v(creative_size, reversed_size)
)
SELECT mt.name
    ,COALESCE(cst.creative_size, rcst.creative_size, mt.banner_w || 'x' || mt.banner_h) as NEW_CREATIVE_SIZE
    ,cst.creative_size AS cst_creative_size
    ,rcst.creative_size AS rcst_creative_size
    ,rcst.reversed_size AS rcst_reversed_size
FROM my_table mt
LEFT JOIN creative_size_table cst ON CONTAINS(mt.name, cst.creative_size)
LEFT JOIN reverse_creative_size_table rcst ON CONTAINS(mt.name, rcst.reversed_size)
ORDER BY 1;

给出:

NAME                         NEW_CREATIVE_SIZE        CST_CREATIVE_SIZE         RCST_CREATIVE_SIZE         RCST_REVERSED_SIZE
320x480_Toyota               320x480                  320x480                   NULL                       NULL
Mcdonalds_320x1024           1024x320                 NULL                      1024x320                   320x1024
Tim_Horton_IO00122_1024x320  1024x320                 1024x320                  NULL                       NULL
Walmart_IO00134              80x80                    NULL                      NULL                       NULL

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM