请帮我重新设计以下查询以改善效果 -
select
LT.id,
LT.SalesAmount,
RT.DiscountAmount,
(LT.SalesAmount - isnull(RT.DiscountAmount,0.00)) as FinalAmount
from @LeftTable as LT
left join @RightTable as RT on RT.id = LT.id
where (LT.SalesAmount - isnull(RT.DiscountAmount,0.00)) > 0
注意 - 上面的查询并不完全是那个创建性能问题的查询,但我简化了它以便在这里更好地解释它。
我发现问题是,当我们在带有右表列的where子句中使用ISNULL时,即isnull(RT.DiscountAmount,0.00)
。
所以,我正在寻找替代上述查询,我们可以从where子句中删除isnull
。
输入数据 -
declare @LeftTable table (id int, SalesAmount decimal(10,2))
declare @RightTable table (id int, DiscountAmount decimal(10,2))
insert into @LeftTable (id, SalesAmount)
select 1, 10.00
union all
select 2, 20.00
union all
select 3, 50.00
insert into @RightTable (id, DiscountAmount)
select 3, 5.00
union all
select 5, 10.00
需要输出 -
id SalesAmount DiscountAmount FinalAmount
1 10.00 NULL 10.00
2 20.00 NULL 20.00
3 50.00 5.00 45.00
实际查询类似于 -
select
col1, col2,.....
from Table1 T1
inner join Table2 T2 on T2.id = T1.id
inner join dbo.functionName(@variable1) f1 on f1.id = T2.id
...................
left join (select col1, col2
from table3 T3
inner join dbo.functionName(@variable2) f2 on f2.id = T3.id) T4
......................
where
T2.col1 + isnull(t4.col2, 0.0) > 0
and .................
希望所以我在这里提到了所有细节,因为这就是我所拥有的(实际上我的同事正面临这个问题而我正在努力帮助他)。
答案 0 :(得分:1)
你可以尝试这样的东西,它会消除ISNULL函数,但它会引入类似UNION的行为。
(
(LT.SalesAmount > 0 AND RT.DiscountAmount IS NULL)
OR (LT.SalesAmount - RT.DiscountAmount > 0)
)
答案 1 :(得分:0)
这是一个简单的方法:
where (RT.DiscountAmount IS NOT NULL AND LT.SalesAmount - RT.DiscountAmount > 0)
OR
(RT.DiscountAmount IS NULL AND LT.SalesAmount > 0)
答案 2 :(得分:0)
您可以尝试以下内容:
;WITH JoinResults AS
(
SELECT
LT.id,
LT.SalesAmount,
RT.DiscountAmount,
LT.SalesAmount,
RT.DiscountAmount,
LT.SalesAmount - RT.DiscountAmount as FinalAmount
FROM
@LeftTable as LT
left join @RightTable as RT on RT.id = LT.id
)
SELECT
*
FROM
JoinResults AS J
WHERE
(J.DiscountAmount IS NULL AND J.SalesAmount > 0) OR
J.FinalAmount > 0
答案 3 :(得分:0)
尝试
declare @LeftTable table (id int primary key, SalesAmount decimal(10,2));
declare @RightTable table (id int primary key, DiscountAmount decimal(10,2));
insert into @LeftTable (id, SalesAmount) values
(1, 10.00)
, (2, 20.00)
, (3, 50.00);
insert into @RightTable (id, DiscountAmount) values
(3, 5.00)
, (2, 25.00)
, (5, 10.00);
select lt.id, lt.SalesAmount, rt.DiscountAmount, lt.SalesAmount - isnull(rt.DiscountAmount, 0) as net
from @LeftTable lt
left join @RightTable rt
on lt.id = rt.id
where (LT.SalesAmount - isnull(RT.DiscountAmount,0.00)) > 0;
select lt.id, lt.SalesAmount, rt.DiscountAmount, lt.SalesAmount - rt.DiscountAmount as net
from @LeftTable lt
join @RightTable rt
on lt.id = rt.id
where (LT.SalesAmount - RT.DiscountAmount) > 0
union all
select lt.id, lt.SalesAmount, null, lt.SalesAmount as net
from @LeftTable lt
left join @RightTable rt
on lt.id = rt.id
where LT.SalesAmount > 0
and rt.id is null;
答案 4 :(得分:0)
用变量表替换子查询并使用变量表来保存子查询数据可以提高性能。
这是我们的方法 -
declare @xyz table (col1 int, col2 int)
insert into @xyz (col1, col2)
select col1, col2
from table3 T3
inner join dbo.functionName(@variable2) f2 on f2.id = T3.id
select
col1, col2,.....
from Table1 T1
inner join Table2 T2 on T2.id = T1.id
inner join dbo.functionName(@variable1) f1 on f1.id = T2.id
...................
left join @xyz T4
......................
where
T2.col1 + isnull(t4.col2, 0.0) > 0
and .................
感谢@Xedni的评论。