问题:我们想要从数据库中删除拼写错误的地址。但我们手头有很多东西要做。所以相反,我有一个函数FN,如果两个地址看起来非常相似(表示可能的拼写错误),则返回true。一个简单的检查是做一些像......
select *
from
address adr1
join address adr2
on FN(adr1, adr2)
但是,这基本上是交叉连接并比较行。由于我们的桌子有多大(> 100万行),这是不可能做到的。但是,我可以限制它只查看彼此附近的地址。例如,同一城市内的地址。所以,我尝试通过这样做来计算这样的地址......
select count(1)
from
address adr1
join address adr2
on adr1.zip = adr2.zip
and adr1.city = adr2.city
--Don't want to compare to self
and adr1.ID <> adr2.ID
问题是这需要太长时间才能运行(我已经等了,但仍然没有完成)。我怀疑oracle有更好的方法来处理大量行的这类事情,但我只是不知道。
那么,如果有办法限制加入的内容(例如只查看相同的邮政编码),那么一个人如何加入一个极大的表呢?
P.S。数万亿条记录是大数据还是应该删除标记?
Edit1:Zip和City已经编入索引。
Edit2:Zip和City都有大量的空值200,000+。这可能会影响索引在连接中的使用方式。
解释计划:
SELECT STATEMENT ALL_ROWSCost: 35,301 Bytes: 42 Cardinality: 1
4 SORT AGGREGATE Bytes: 42 Cardinality: 1
3 HASH JOIN Cost: 35,301 Bytes: 2,195,769,492 Cardinality: 52,280,226
1 TABLE ACCESS FULL TABLE SCHEMA.ADDRESS Cost: 15,677 Bytes: 21,388,962 Cardinality: 1,018,522
2 TABLE ACCESS FULL TABLE SCHEMA.ADDRESS Cost: 15,677 Bytes: 21,388,962 Cardinality: 1,018,522
Edit3:我已经尝试过以不同的方式计算行数。
select
sum(cnt * (cnt - 1))
from
(
select
count(1) as CNT
from schema.address adr1
group by adr1.zip, adr1.city
)
这在不到10秒的时间内返回了大约450亿个不同的配对。我不确定我的函数每秒可处理超过10万行,这是在12小时内运行所需的行。
答案 0 :(得分:1)
1)在字段ZIP
和CITY
2)要获得重复项(这是您在第二种情况下的操作),请使用GROUP BY
:
SELECT ZIP,CITY, count(*) FROM ADDRESS HAVING COUNT(*)>1 GROUP BY ZIP,CITY
答案 1 :(得分:1)
我有一些好消息,还有一些坏消息。
好消息是,您现有的查询可能接近50亿行,而不是450亿行。
坏消息是,这是因为它不会尝试匹配具有null zip或null city值的200,000条记录中的任何一条 - Oracle(以及我知道的所有其他RDBMS)都不会将NULL值连接到其他NULL值;有关示例,请参阅here。您可以使用coalesce
作为加入条件的一部分来解决此问题,但我建议您分别处理空城/邮编记录。
假设您的函数对称地处理地址(以便FN(addr1,addr2)
返回与FN(addr2,addr1)
相同的结果),您可以通过将adr1.ID <> adr2.ID
更改为{{1}来进一步减少组合数量的一半在您现有的查询中。如果您还没有合适的索引,我建议在zip,city和id上添加一个(按此顺序)。
答案 2 :(得分:0)
另一种方法是使用邮政编码idcode编码每个地址,如果存在相关地址/国家/地区。这意味着,不是将每个地址与自身进行比较,而是首先将所有精力放在解析和解码地址上。我们使用这种方法,并将id存储在每一行中,这意味着我们可以在以后非常精确和快速地加入。
如果您不能使用邮政ID(并且我的意思是邮局指定的每个送货地址的唯一身份证),则考虑对每个地址进行地理编码,然后通过地址附近的地址加入。如果地址不是纯粹的邮政地址,地理编码也可能适用。
我对FN()对地址的作用非常感兴趣,您是否看到http://www.mjt.me.uk/posts/falsehoods-programmers-believe-about-addresses/与您的问题无关,但如果您不熟悉地址处理,请阅读良好。