简体   繁体   English

如何在SQL的WHERE中使用COALESCE?

[英]How to use COALESCE in WHERE in SQL?

In the scenario where I have a dataset like so, and I need a Coalesce as to speak, within the WHERE clause. 在我有这样的数据集且需要在WHERE子句中说的合并的情况下。

The requirement is to filter where if there is a row with Type Actual, filter out the type of Expected. 要求是过滤是否存在“实际类型”行,过滤掉“期望”类型。 Please see dataset below which should make things clearer 请查看下面的数据集,这应该使事情更清楚

Table Parent Record (GUID), Type (text), Date (datetime) 父记录 (GUID), 类型 (文本), 日期 (日期时间)

Actual Data 实际数据

  1. 100, ABC Active, 01/01/2010 100,ABC Active,01/01/2010
  2. 100, ABC Draft, 01/01/2010 100,ABC草案,01/01/2010
  3. 100, DEF Draft, 01/01/2010 100,DEF草稿,2010年1月1日
  4. 100, GHI Active, 01/01/2010 100,GHI Active,01/01/2010
  5. 100, GHI Draft, 01/01/2010 100,GHI草案,01/01/2010

Expected Results 预期成绩

  1. 100, ABC Active, 01/01/2010 100,ABC Active,01/01/2010
  2. 100, DEF Draft, 01/01/2010 100,DEF草稿,2010年1月1日
  3. 100, GHI Active, 01/01/2010 100,GHI Active,01/01/2010

As you can see, where there is a row with type Active , for a certain type, then the Draft is removed. 如您所见,对于某个类型,在其中存在类型为Active的行,然后将Draft删除。 If there is no type with an Active row, then just show the Draft . 如果没有带有Active行的类型,则仅显示Draft

could someone please help with the WHERE clause for this 有人可以为此提供WHERE子句吗

I think you need conditional ordering : 我认为您需要条件排序:

select top (1) with ties t.*
from table t
order by row_number() over (partition by ParentRecord, col
                            order by (case when Type = 'Active'
                                           then 1 
                                           else 2
                                      end)
                           );

This assumes type column doesn't have a other data like you have posted. 假设type列没有您发布的其他数据。

You want filtering . 您要过滤。 . . but I don't see where coalesce() comes in. One way to do what you want is: 但是我看不到coalesce()用处。一种执行所需操作的方法是:

select t.*
from t
where t.type = 'Active'
union all
select t.*
from t
where t.type = 'Draft' and
      not exists (select 1 from t t2 where t2.guid = t.guid);

You can express this in a single query as: 您可以在单个查询中将其表示为:

select t.*
from t
where (t.type = 'Active') or
      (t.type = 'Draft' and
       not exists (select 1 from t t2 where t2.guid = t.guid)
      );

It would be simpler if the 'Active' and 'Draft' status were stored in a separate column since this would avoid taking sub-strings in the Type column. 如果将“活动”和“草稿”状态存储在单独的列中会更简单,因为这样可以避免在“类型”列中使用子字符串。 There's actually not much in the WHERE clause. 实际上,WHERE子句中没有太多内容。

Using a temp table for example: 例如使用临时表:

DECLARE @temp TABLE (GUID int, Type varchar(100), Date datetime)
INSERT INTO @temp VALUES
 (100, 'ABC Active', '01/01/2010'), (100, 'ABC Draft', '01/01/2010')
,(100, 'DEF Draft', '01/01/2010'), (100, 'GHI Active', '01/01/2010')
,(100, 'GHI Draft', '01/01/2010'), (100, 'JKL Active', '01/01/2010')

SELECT T.GUID
      ,COALESCE( (SELECT T2.Type
                    FROM @temp T2
                   WHERE T2.GUID = T.GUID
                     AND T2.Type LIKE '%Active'
                     AND LEFT(T.Type, 3) = LEFT(T2.Type, 3)
                  ) 
                   , T.Type
                ) AS [Type]
      ,T.Date
  FROM @temp T
 WHERE T.Type LIKE '%Draft'

Produces the expected output: 产生预期的输出:

GUID    Type         Date
100     ABC Active   2010-01-01 00:00:00.000
100     DEF Draft    2010-01-01 00:00:00.000
100     GHI Active   2010-01-01 00:00:00.000

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

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