是否可以在与PARTITION BY相同的查询中使用WHERE子句?

时间:2012-12-06 15:33:24

标签: teradata

我需要编写一个SQL,它只保留表中每条可识别记录的最少5条记录。为此,我使用partition by并删除返回值大于5的所有记录。当我尝试在与partition by语句相同的查询中使用WHERE子句时,我收到错误“Ordered WHERE子句中不允许使用分析函数“。所以,为了让它工作,我必须使用三个子查询。我的SQL看起来像这样:

delete mydb.mytable where (field1,field2) in
(
    select field1,field2 from
    (
        select field1,field2,
        Rank() over
        (
            partition BY field1
            order by field1,field2
        ) n 
        from mydb.mytable
    ) x
    where n > 5
)

最里面的子查询只返回原始数据。由于我不能在那里使用WHERE,我用子查询包装它,其目的是1)使用WHERE获取大于5的记录,2)只选择field1和field2。我只选择这两个字段的原因是我可以使用IN语句删除最外层查询中的那些记录。

它有效,但看起来有点麻烦。我想将内部两个子查询合并为一个子查询。这可能吗?

1 个答案:

答案 0 :(得分:1)

听起来你需要使用QUALIFY子句,它是Window Aggregate函数的HAVING子句。以下是我对你想要完成的事情的看法。

如果没有先测试,请不要直接针对您的生产数据运行此SQL。

/* Physical Delete */
DELETE TGT
  FROM MyDB.MyTable TGT
 INNER JOIN
       (SELECT Field1
             , Field2
        FROM MyDB.MyTable
        QUALIFY ROW_NUMBER() (PARTITION BY Field1, ORDER BY Field1,2)
              > 5
       ) SRC
    ON TGT.Field1 = SRC.Field1
   AND TGT.Field2 = SRC.Fileld2

/* Logical Delete */
UPDATE TGT
  FROM MyDB.MyTable TGT
     ,
       (SELECT Field1
             , Field2
        FROM MyDB.MyTable
        QUALIFY ROW_NUMBER() (PARTITION BY Field1, ORDER BY Field1,2)
              > 5
       ) SRC
   SET Deleted = 'Y'
    /* RecordExpireDate = Date - 1 */
 WHERE TGT.Field1 = SRC.Field1
   AND TGT.Field2 = SRC.Fileld2