您好,欢迎访问一九零五行业门户网

Cont()与Where().Count()有时性能差别如此之大!

今天在修改后台用户公司管理列表时,发现列表加载超慢的bug!好几十秒啊!数据是相对其他的列表是稍微多点,不过也就4000多条,之前是好的,为啥这么慢呢?
想起我之前在此列表中加入了一个字段,用于方便提示管理员公司的产品列表是否有修改之类的状态字段,于是可以断定是加了此字段的原因。
首先,先看看我之前是如何写这个提示状态字段的,实体中加入contentstatus,然后直接在linq语句中select 实体对象中加入contentstatus=product_maintain.count(c => c.companyid == company.id && c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4))>0?产品有更新:。这时我想应该是加入三元运算,linq在转sql时,产生过多的,case,when ,then语句,三元运算增加了判断会影响查询性能,于是我去掉后,再运行查看页面,仍然很慢,感觉不出快了多少。
这时,我想起了linqpad,看看到底转换生成了怎样的sql语句。运用count(条件)生成sql代码如下:
代码如下:
select count(*) as [value]
from (
select
(case
when ([t1].[companyid] = ([t0].[id])) and ([t1].[isdeleted] = @p0) and (([t1].[auditstatus] = @p1) or ([t1].[auditstatus] = @p2)) then 1
when not (([t1].[companyid] = ([t0].[id])) and ([t1].[isdeleted] = @p0) and (([t1].[auditstatus] = @p1) or ([t1].[auditstatus] = @p2))) then 0
else null
end) as [value]
from [company_product_maintain] as [t1]
) as [t2]
where [t2].[value] = 1
这时我发现一个很简单的count的sql 语句,linq转换后变得如此复杂,我直接在sql server中运行此代码,发现查询还是很慢,于是我直接把contentstatus=product_maintain.where(c => c.companyid == company.id && c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4)).count()生成sql语句为:
代码
代码如下:
select count(*) as [value]
from [gassns_company_equipment_maintain] as [t1]
where ([t1].[companyid] = ([t0].[id])) and ([t1].[isdeleted] = @p0) and (([t1].[auditstatus] = @p1) or ([t1].[auditstatus] = @p2))
发现运行速度那是快了一个数量级啊!
后台列表查询结果速度大大提升有图为证(): 图1为count结果,用了35秒,哇塞!
图2为where(条件).count()结果,同样的数据只用了4秒钟,差了10倍!
然后为了取值方面我还是加入三元运算,contentstatus=product_maintain.where(c => c.companyid == company.id && c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4)).count()>0?产品有更新:。结果如下:
真的是count()与 where()区别,不可能这么大差距吧?于是我单写 product_maintain.where(c => c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4)).count() 与 product_maintain.count(c => c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4)) 发现速度差不多,生成的代码是一样的。
代码如下:
select count(*) as [value]
from [gassns_company_equipment_maintain] as [t0]
where ([t0].[isdeleted] = @p0) and (([t0].[auditstatus] = @p1) or ([t0].[auditstatus] = @p2))
原来是我如果在select中取某表的数量并且条件中使用了之前from后的某个变量时,这时用count(条件)和where(条件).count()产生代码才会不同,查询速度才会出现数量级的差别。
代码
代码如下:
//效率低版本:
from company in company
select new
{
contacter = v.contacterid,
count = product_maintain.count(c => c.companyid == company.id &&c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4))
}

代码如下:
//效率高版本:
from company in company
select new
{
contacter = v.contacterid,
count = product_maintain.where(c =>c.companyid == company.id && c.isdeleted == 0 && (c.auditstatus == 0 || c.auditstatus == 4)).count()
}
否则,count()与where().count()生成的sql语句是相同的,效率也一样。 总结到此,望各位看官以后要注意!本人入园两年来,第一发在首页,请各位看官不吝赐教! 以上查询图都linqpad查询结果截图。至于为啥4秒左右为linqpad查询时间,linq生成sql语句在sql server中执行不到1秒,以下截图作解释:
其它类似信息

推荐信息