UPDATE j
SET j.Price=(SELECT TOP 1 ISNULL(m.Price,0) FROM i
INNER JOIN g ON g.CID=i.CID
INNER JOIN m ON m.CID IN
(
SELECT * FROM fun_split(ISNULL(g.FullCIDPath,''),'\')
)
INNER JOIN g2 ON g2.CID=m.CID
WHERE i.cname =j.cname AND (m.stid=j.stid OR ISNULL(m.stid,-1)=-1)
AND (m.spfid=2 OR ISNULL(m.spfid,-1)=-1)
ORDER BY g2.clevel DESC,ISNULL(m.stid,-1) desc,ISNULL(m.spfid,-1))
FROM j
WHERE j.price =0
假设CID有三级,例如FullCIDPath为 1\10\100
1、10、100分别代表第一、二、三级的CID,
上面的这种写法效率有点低,怎样写效率高?
------解决方案--------------------
如果是2K5以上 可以考虑用cross apply 这种,不用子查询。
MCID 可用LIKE
------解决方案--------------------
ON m.CID IN
(
SELECT * FROM fun_split(ISNULL(g.FullCIDPath,''),'\')
)
改为
ON '%\'+m.CID+'\%' like '\'+g.FullCIDPath+'\'
结果是否一样,速度有无提高?
------解决方案--------------------
优化建议:
1.为避免锁争阻塞,减少锁表时间,
建议拆分为2步,先查询出结果存为临时表,然后关联目标表做更新.
2.从函数名看,fun_split()应该是按指定的分隔符分隔字符串为列数据?
应该可用charindex()函数代替,g.FullCIDPath上应有索引.
3.where子句中使用or逻辑运算符,执行计划会偏向于全表扫描.
应该避免使用.