我有下面的代码...提高性能SP
UPDATE Sales
SET MappingOrderID = CAST ([dbo].[fRemoveNonNumericCharacters] (ltrim(rtrim(ActualOrderNumber))) AS INT)
FROM Sales
where isnumeric(ActualOrderNumber) = 1
and ActualOrderNumber not like '%.%'
and len(ActualOrderNumber) < 10
and MappingOrderID is null
and ActualOrderNumber is not null
and ltrim(rtrim(ActualOrderNumber)) in (select ltrim(rtrim(OrderID)) from dbo.Orders)
参与的栏目有:
销售: MappingOrderId INT ActualOrderNumber NVARCHAR(10)
从订单: 的OrderId INT
这是遗留代码,我是DBA,我不知道他/她为什么使用T轮圈这么多...脚本需要9分钟跑,理想必须频繁地运行......
我也是在执行计划中得到这样的:
CONVERT_IMPLICIT(VARCHAR(12),[数据集市] [DBO]。[指令]。[订单ID],0)
CONVERT_IMPLICIT(VARCHAR(20),[Datamart的]。[DBO]。[销售]。[ActualOrderNumber],0)
表达式中的类型转换(CONVERT_IMPLICIT(varchar(20),[DataMart]。[dbo]。[Sales]。[ActualOrderNumber],0) )可能会影响查询计划选择中的“CardinalityEstimate”,表达式中的类型转换(CONVERT_IMPLICIT(varchar(12),[Datamart]。[dbo]。[Orders]。[OrderID],0))可能会影响查询计划中的“CardinalityEstimate”选择
对于我感觉到...
它更新MappingOrderId(INT)铸造ActualOrderNumber(VARCHAR)...这将只有ActualOrderNumber在订单存在更新...
我尝试了一些修改;但VARCHAR ActualOrderNumber有一个像3545427103值,如果我尝试删除像什么:
and len(ActualOrderNumber) < 10
这将打破...
我的总体目标是使这一进程的最有效的可能;在源头上修复数据是唯一真正的解决方案?
我实施了很多建议,并且下降到了一分钟。谢谢!但我不明白的是:
现在我有更多的读取...它需要几秒钟跑......这怎么可能?
LIKE也非常昂贵。如果你知道逻辑,肯定有办法改进这个查询。这是在订单号字段中检查美元价值吗?这可以更改为CONTAINS。怎么了只返回长度小于10的订单号呢? –
如果您有机会,请将包含已清理的订单号的列添加到两个表中,然后对其进行填充并将其编入索引。总共花费的时间可能不会少于九分钟。在将最后的'IN'更改为'exists'时,您可能会看到一些优势,但请检查更改之间的查询计划。 –
哦,你也有一个UDF可能会放慢速度。查询计划应该给你一些想法。要计算CardinalityEstimate是否真的受到影响,请比较实际和估计计划,并查看行数是否在相同的附近 –