我正在尝试优化以下 LINQ 查询,性能是主观的,因此下面提供有关这方面的一些详细信息。
Dim _calls = (From p In db.PhoneLogs.AsNoTracking Where
p.from_caller_id.Contains(Phone1) Or p.to_caller_id.Contains(Phone1) _
p.from_caller_id.Contains(Phone2) Or p.to_caller_id.Contains(Phone2) _
).ToList()
鉴于以下情况:
from/to_caller_id
列是字符串,值可以是:915555555555
或JOHNNY <5555555555>
或915555555555
Phone1
被解析为 10 位数字,删除任何前导 +1
例如:5555555555
Phone2
被解析为 12 位数字,删除任何前导 +
例如:915555555555
性能
我认为最好的选择是使用原始 SQL,因为这样你就可以这样做:
SELECT p.*
FROM AsNoTracking p
INNER JOIN (VALUES
(@Phone1),
(@Phone2)
) filter(Phone) ON CONTAINS(p.from_caller_id, filter.Phone)
OR CONTAINS(p.to_caller_id, filter.Phone)
这使得扩展至任意数量的输入或将
OR
切换为 UNION
变得更简单,这可能会表现得更好。但我还没有找到让 Linq 生成这样的东西的方法。
它还强调了它缓慢的一个重要原因:输入周围的前导通配符破坏了使用索引来帮助此查询的任何机会。