2017-08-12 25 views
0

得到重复的记录我有如下与结构表: Tabel Structure无法从表

为user_id具有值在特定的时间间隔各自的项目。项目值可以是文本或整数取决于项目。

我想检查是否有任何两个或多个UserId为相同的值,这意味着它们的项目在相同的值和相同的时间间隔内是相同的。

如上表所示UserId 213456和UserId 213458具有相同的记录。 我试过使用游标和循环,但它花费的时间太长。我的表有超过5000万UserId。有没有办法以有效的方式做到这一点?

我也尝试使用group by子查询,但所有的尝试都未能创建一个好的查询。

我创建使用How do I find duplicate values in a table in Oracle?

select t1.USERID, count(t1.USERID) 
from USERS_ITEM_VAL t1 
where exists (select * 
       from USERS_ITEM_VAL t2 
       where t1.rowid <> t2.rowid and 
         t2.ITEMID = t1.ITEMID and 
         t2.TEXT_VALUE = t1.TEXT_VALUE and 
         --t2.INTEGER_VALUE = t1.INTEGER_VALUE and 
         t2.INIT_DATE = t1.INIT_DATE and 
         t2.FINAL_DATE = t1.FINAL_DATE) 
     group by t1.USERID having count(t1.USERID) > 1 order by count(t1.USERID); 

下面的查询,但问题是它的工作不包括INTEGER_VALUE列,但不给我输出的时候,当我包括在INTEGER_VALUE列的加入,虽然我在INTEGER_VALUE列数据是一样的。 这里是我的表的结构:接近这个利用自加入

USERID - NUMBER 
ITEMID - NUMBER 
TEXT_VALUE - VARCHAR2(500) 
INTEGER_VALUE - NUMBER 
INIT_DATE - DATE 
FINAL_DATE - DATE 
+0

https://stackoverflow.com/questions/59232/how-do-i-find-duplicate-values-in-a-table-in-oracle –

回答

0

的一种方式。这个想法是计算两个用户共同的项目数(考虑日期列)。然后比较这对项目的数量,每个有:

with t as (
     select t.*, count(*) over (partition by userid) as numitems 
     from t 
    ) 
select t1.userid, t2.userid 
from t t1 join 
    t t2 
    on t1.userid < t2.userid and 
     t1.itemid = t2.itemid and 
     t1.init_date = t2.init_date and 
     t1.final_date = t2.final_date and 
     t1.numitems = t2.numitems 
group by t1.userid, t2.userid, t1.numitems 
having count(*) = t1.numitems; 
+0

感谢您的帮助,但它没有奏效 – John

0

查询失败的原因是,要么TEXT_VALUE或integer_value将每一行中NULL。出于这个原因,不可能在自联接中使用相等谓词而不使用NVL函数来插入NULL值。

然而,下面是使用的解析函数来完成目标的查询:

Select * From (
Select t.*, Count(*) Over (Partition By t.itemId, 
             t.text_value, 
             t.integer_value, 
             t.init_date, 
             t.final_date) as Cnt) 
Where cnt > 1; 

查询返回在多个的记录在Partition By条款的五列相同值的所有行。

这种技术优于自联接方法的好处是该表只扫描一次,而使用自联接进行两次扫描。如果表格很大,这可能会带来更好的性能。