调用多个列的条件(与NAS)的SQL查询(SQL query for calling multipl

2019-09-29 09:38发布

这是从我的一个连续的问题前面的问题 。 我想写一个SQL查询,要求有条件的几列。 我使用RMySQL包R上工作室工作。 我的服务器是MySQL的。

该表看起来是这样的。

organisation          A           B           C           D
Ikea         2018-04-01  2018-05-07  2018-05-09  2018-05-01
Ikea         2018-06-01  2018-05-03  2018-05-29          NA   
Orange       2018-04-02  2018-05-01  2018-07-08  2018-05-26 
Ikea         2018-06-02  2018-05-01          NA  2018-05-26
Nestle       2018-06-02  2018-05-01          NA  2018-05-26
Ikea                 NA  2018-05-05  2018-04-02  2018-06-01

我希望得到一个列,其中组织是宜家,并在四列(A,B,C,d)中最早的日期是2018年5月1日和2018年5月31日之间。

在其中包含NA值的行,我想忽略了NAS与看看有什么价值的其余部分中最早的日期。 例如,对于第二行,最早日期是“2018年5月3日”(B栏),因此它满足标准。

因此,只有在第二原始表的第四行上述匹配的条件。 而结果,我想应该是:

organisation          A           B           C           D
Ikea         2018-06-01  2018-05-03  2018-05-29          NA    
Ikea         2018-06-02  2018-05-01          NA  2018-05-26

我应该如何编写一个SQL查询? 下面是从我刚才的问题得到答案后,我的尝试,但它不用于NAS行工作。

SELECT * FROM myTable 
WHERE organisation LIKE Ikea
LEAST(A, B, C, D) >= '2018-05-01' AND
LEAST(A, B, C, D) < '2018-06-01'

谢谢你的任何种类的帮助!

Answer 1:

只要使用coalesce()

SELECT *
FROM myTable 
WHERE organisation LIKE 'Ikea' AND
      LEAST(COALESCE(A, '2019-01-01'), COALESCE(B, '2019-01-01'), COALESCE(C, '2019-01-01'), COALESCE(D, '2019-01-01')) >= '2018-05-01' AND
      LEAST(COALESCE(A, '2019-01-01'), COALESCE(B, '2019-01-01'), COALESCE(C, '2019-01-01'), COALESCE(D, '2019-01-01')) < '2018-06-01';

'2019-01-01'是范围之后的任意时间。



Answer 2:

你可以尝试使用IFNULL()的值,并使用getdate()所以如果它是零它只是今天使用的,然后该不会是认为它基本上忽略了他们的最少。

像: LEAST(IFNULL(A,getdate()), IFNULL(B,getdate()), IFNULL(C,getdate()), IFNULL(D,getdate()))

希望这可以推动你在正确的方向

除非NA是有一个字符串,你可以使用一个case语句类似case when A = 'NA' THEN getdate() end

最终可能看起来像

SELECT * FROM myTable 
WHERE organisation LIKE Ikea
LEAST(IFNULL(A,getdate()), IFNULL(B,getdate()), IFNULL(C,getdate()), IFNULL(D,getdate())) >= '2018-05-01' AND
LEAST(IFNULL(A,getdate()), IFNULL(B,getdate()), IFNULL(C,getdate()), IFNULL(D,getdate())) < '2018-06-01'

要么

SELECT * FROM myTable 
WHERE organisation LIKE Ikea
LEAST(case when A = 'NA' THEN getdate() else A end, case when B = 'NA' THEN getdate() else B end, case when C = 'NA' THEN getdate() else C end, case when D = 'NA' THEN getdate() else D end) >= '2018-05-01' AND
LEAST(case when A = 'NA' THEN getdate() else A end, case when B = 'NA' THEN getdate() else B end, case when C = 'NA' THEN getdate() else C end, case when D = 'NA' THEN getdate() else D end) < '2018-06-01'


Answer 3:

考虑加入上使用派生的汇总查询UNION ALL

SELECT m.*
FROM myTable m
INNER JOIN 
   (SELECT t.ID, MIN(t.`DateValue`) As MinDate
    FROM 
       (SELECT ID, organisation, 'A' As 'Category', A As `DateValue` FROM myTable
        UNION ALL
        SELECT ID, organisation, 'B' As 'Category', B As `DateValue` FROM myTable
        UNION ALL
        SELECT ID, organisation, 'C' As 'Category', C As `DateValue` FROM myTable
        UNION ALL
        SELECT ID, organisation, 'D' As 'Category', D As `DateValue` FROM myTable) As t
    WHERE t.organisation = 'Ikea'
    GROUP BY t.ID
    HAVING MIN(t.`DateValue`) >= '2018-05-01' AND MIN(t.`DateValue`) < '2018-06-01') As agg
ON m.ID = agg.ID;

RexTester演示 (注:日期是DD-MM-YYYY格式)



文章来源: SQL query for calling multiple columns with conditions(with NAs)