【SQL优化】一个生产线上剔重SQL的优化
2015-10-15 09:23
429 查看
在我们生产上有个表,记录的是工单派发的中间状态,派单程序各个模块之间会根据这个状态表分别对工作单执行不同的派法任务。
很明显在这个表中,根据工作任务单不允许重复。
但是很多时候,开发侧在设计的时候都不加主键(原因是害怕应用代码上报错,我去),所以我们需要定时去描述这个表,把重复的记录给删除。
而之前的删除代码是这样写的:
delete aiadmin.cct_trans_eomsintf
where rowid in
(select e.rod
from (select o.rowid as rod, o.accept_id
from aiadmin.cct_trans_eomsintf o,
(select a.rowid as rid, a.accept_id
from aiadmin.cct_trans_eomsintf a,
(select accept_id, min(id) as creation_id
from aiadmin.cct_trans_eomsintf
group by accept_id
having count(accept_id) > 1) b
where a.accept_id = b.accept_id
and a.id = b.creation_id) d
where o.accept_id = d.accept_id
and o.rowid != d.rid
order by o.accept_id) e)
很明显,这个sql执行时要全表扫描trans表三次,最后一次使用rowid回表再删除记录。
因为这个中间表的记录不是很多,所以效率上并没有什么伤害。
但其实,下面的写法更高效:
delete from aiadmin.cct_trans_eomsintf w
where w.rowid in (select new_rowid
from (select eos.rowid as new_rowid,
row_number() over(partition by eos.accept_id order by eos.id, eos.rowid) as rid
from aiadmin.cct_trans_eomsintf eos)
where rid <> 1)
其只需要对trans表做一次全表扫描,效率明显高出很多。
ps,这里是根据accept_id重复就判定为重复,如果需要根据多个字段(或者全部字段)来判定为重复,那么在分组排序时需要将相应的字段全部加上。
很明显在这个表中,根据工作任务单不允许重复。
但是很多时候,开发侧在设计的时候都不加主键(原因是害怕应用代码上报错,我去),所以我们需要定时去描述这个表,把重复的记录给删除。
而之前的删除代码是这样写的:
delete aiadmin.cct_trans_eomsintf
where rowid in
(select e.rod
from (select o.rowid as rod, o.accept_id
from aiadmin.cct_trans_eomsintf o,
(select a.rowid as rid, a.accept_id
from aiadmin.cct_trans_eomsintf a,
(select accept_id, min(id) as creation_id
from aiadmin.cct_trans_eomsintf
group by accept_id
having count(accept_id) > 1) b
where a.accept_id = b.accept_id
and a.id = b.creation_id) d
where o.accept_id = d.accept_id
and o.rowid != d.rid
order by o.accept_id) e)
很明显,这个sql执行时要全表扫描trans表三次,最后一次使用rowid回表再删除记录。
因为这个中间表的记录不是很多,所以效率上并没有什么伤害。
但其实,下面的写法更高效:
delete from aiadmin.cct_trans_eomsintf w
where w.rowid in (select new_rowid
from (select eos.rowid as new_rowid,
row_number() over(partition by eos.accept_id order by eos.id, eos.rowid) as rid
from aiadmin.cct_trans_eomsintf eos)
where rid <> 1)
其只需要对trans表做一次全表扫描,效率明显高出很多。
ps,这里是根据accept_id重复就判定为重复,如果需要根据多个字段(或者全部字段)来判定为重复,那么在分组排序时需要将相应的字段全部加上。
相关文章推荐
- PowerDesigner生成mysql字段comment注释
- memcached(三)--stats
- MFC对话框以ADO的方式连接(ACESS)数据库
- 数据库异常:“Column 'CODE' in where clause is ambiguous”
- MySql:备份与恢复数据库
- SQL中Left Join 与Right Join 与 Inner Join 与 Full Join的区别
- ORACLE之ASM概念
- oracle多表查询
- iOS中的数据库应用
- 多mysql环境(wamp和单独配置的环境同时存在)如何使用这个环境
- ubuntu install mysql
- oracle.jdbc.driver.OracleDriver和oracle.jdbc.OracleDriver这两个驱动的区别
- win8 下免安装版mysql
- SQL 2008R2本地连接历程
- 【转载,有批注】sqlite的线程安全问题
- MySql调优
- 数据库中间件
- 实现Asp.net Mvc分布式Session Redis群集
- 通用二进制安装MySQL(MariaDB)
- Hibernate.initialize(Obj)用法