SQL - 如何从同一个表

时间:2017-05-10 14:57:34

标签: sql sql-server

您有一个包含userID列和2个函数列的表。 该表有1亿行和10个成千上万的用户。

enter image description here

问题是每个用户的function1和function2都是重复的,但功能顺序相反。 I.E.用户= 1000具有F1 = 5,F2 = 10但是F2 = 10,F2 = 5。因此,如果您可以过滤掉这些重复项,则可以节省此表正在使用的空间的大约50%。

为每个用户过滤掉重复功能的最快方法是什么。

3 个答案:

答案 0 :(得分:2)

如果(a,b),(b,a)对存在,您可以使用row_number为用户获取一个此类组合。

select userid,function1,function2 from (
select userid,function1,function2
,row_number() over(partition by userid
                   order by 
                   case when function1<function2 then function1 else function2 end,
                   case when function1>function2 then function1 else function2 end,
                   function1
                  ) as rnum
from tablename
) t
where rnum=1

使用cte删除其中一个对称对组合。

with cte as (select userid,function1,function2
             ,row_number() over(partition by userid
                   order by 
                   case when function1<function2 then function1 else function2 end,
                   case when function1>function2 then function1 else function2 end,
                   function1
                  ) as rnum
            from tablename)
delete from cte where rnum > 1

答案 1 :(得分:1)

要删除所有重复项,您可以按以下方式继续:

添加新列(: random-if-empty (-> (U Image-Color "empty") Image-Color)) (define (random-if-empty s) (cond [(equal? s "empty") (random-color)] [else (assert s string?)])) 并使用唯一值更新它(例如rownum,或者您也可以使用序列)。填充列后,在其上定义PK。

然后您应该能够使用此查询删除重复数据:

temp_pk

之后删除PK和temp_ok列并重新定义PK over UserID,因此未来不会再发生这种情况。

A / B =您的Function1 / Function2列

答案 2 :(得分:1)

首先,当我读到这个问题时,@ TriV的回答是正确的。我不知道为什么它被downvoted或删除。

其次,如果要删除行,您知道所有行都是重复的,那么您可以这样做:

delete from t
    where function1 > function2;

这并不令人满意,因为你想要最快的方法。删除可能很昂贵,因此可能更快:

select *
into temp_t
from t
where function1 < function2;

truncate table t;

insert into t
    select *
    from temp_t;

如果你没有完整的副本,那么你可以用以下的方式做同样的想法:

select *
into temp_t
from t
where function1 < function2
union all
select *
from t t
where function1 > function2 and
      not exists (select 1 from t t2 where t2.function1 = t.function2 and t2.function2 = t.function1);

假设您有t(function1, function2)的索引,后一个表达式可能是获取唯一集合的最快方法。