优化我的 linq 查询,该查询在 azure 查询性能洞察工具中列为消耗量最大的查询

克里希那君·巴诺特

我要优化的 Linq 查询:

var onlineData = (from od in peopleStatus.AsNoTracking().ToList()

let location = (from zone in db.RTLS_ZONEDTLS
                where zone.zone_id == od.Person.Zone_ID
                select zone.area).AsNoTracking().FirstOrDefault()

let zoneIdsArray = getZoneList((od.ZoneIds.ToArray()))
let fzones = zoneIdsArray.Select(z => z).Take(4)

select new OnlineDataInfoDTO
{
    P_ID = od.Person.PERSONID,
    T_ID = (int)od.Person.TAGID,
    Z_ID = (od.Person.created_time >= startOfThisDay) ? (int)od.Person.Zone_ID : -1,
    LOC = (location != null ? location : " "),
    STATUS = (od.Person.created_time >= startOfThisDay) ? (int)od.Person.status : 6,
    T_BAT_SIG_STR = (int)od.Person.TAG_SIGNALSTRENGTH,
    B_BAT_SIG_STR = (int)od.Person.BS_SIGNALSTRENGTH,
    T_BAT_STA_VAL = (int)od.Person.TAG_BATTERY_STATUS_VAL,
    T_BAT_STA_PERCNT = (int)od.Person.TAG_BATTERY_STATUS_PERCNT,
    BS_BAT_STA_VAL = (int)od.Person.BS_BATTERY_STATUS_VAL,
    BS_BAT_STA_PER = (int)od.Person.BS_BATTERY_STATUS_PERCNT,
    IN_TIME = (od.Person.INTIME).ToString(),
    ALL_NOT_TME = (od.Person.ALLISNOTWELLTIME).ToString(),
    P_TME = (od.Person.PANICTIME).ToString(),
    NO_M_TME = (od.Person.NOMOTIONTIME).ToString(),
    OUT_TME = (od.Person.OUT_TIME).ToString(),
    TEMP_TME = (od.Person.TEMPEXCEEDTIME).ToString(),
    LOW_BAT_TME = (od.Person.LOW_BATTERY_TIME).ToString(),
    FOUT_TME = (od.Person.FOUT_TIME).ToString(),
    LAST_UPDATE_TIME = (od.Person.LASTUPDATEDTIME).ToString(),
    TEMP_VAL = (decimal)(od.Person.TEMP_VALUE),


    NO_OF_OUT = (
      from o in db.RTLS_FAULT_DTLS
      where (o.faultno == (int)Constants.Faults.LowBattery)
      where (startOfThisDay <= o.ORC_DATETIME && o.ORC_DATETIME <= todayEndDate)
      where (o.PERSON_ID.ToLower() == od.Person.PERSONID.ToLower())
      select o.fltname).Count(),
    NO_OF_PANIC = (
      from o in db.RTLS_FAULT_DTLS
      where o.faultno == (int)Constants.Faults.Panic
      where (startOfThisDay <= o.ORC_DATETIME && o.ORC_DATETIME <= todayEndDate)
      where (o.PERSON_ID.ToLower() == od.Person.PERSONID.ToLower())
      select o.fltname).Count(),
    NO_OF_IN_ACTIVE = (
      from o in db.RTLS_FAULT_DTLS
      where o.faultno == (int)Constants.Faults.InActive
      where (startOfThisDay <= o.ORC_DATETIME && o.ORC_DATETIME <= todayEndDate)
      where (o.PERSON_ID == od.Person.PERSONID)
      select o.fltname).Count(),
    NO_OF_TEMP = (
      from o in db.RTLS_FAULT_DTLS
      where (o.faultno == (int)Constants.Faults.HighTemp || o.faultno == (int)Constants.Faults.LowTemp)
      where (startOfThisDay <= o.ORC_DATETIME && o.ORC_DATETIME <= todayEndDate)
      where (o.PERSON_ID == od.Person.PERSONID)
      select o.fltname).Count(),
    NO_OF_LBAT = (
      from o in db.RTLS_FAULT_DTLS
      where o.faultno == (int)Constants.Faults.LowBattery
      where (startOfThisDay <= o.ORC_DATETIME && o.ORC_DATETIME <= todayEndDate)
      where (o.PERSON_ID == od.Person.PERSONID)
      select o.fltname).Count(),
    LOCS = fzones.ToList()
}).ToList();

我的 getZoneList 方法如下所示,用于上述查询。

public int[] getZoneList(decimal[] zoneIdsArray)
{
    int[] zoneIds = Array.ConvertAll(zoneIdsArray, x => (int)x);
    List<int> list = zoneIds.ToList();
    for (int c = 1; c < zoneIdsArray.Count(); c++)
    {
        if (zoneIdsArray[c] == zoneIdsArray[c - 1])
        {
            list.Remove((int)zoneIdsArray[c]);
        }
    }
    return list.ToArray();
}

对于我的应用程序,我在 Visual Studio-2015 中使用 WebApi2 编写了一个 Web 服务,实体框架作为 ORM,Azure_SQL 作为后端。我观察到上面的 linq 查询需要最少 25 秒到最多 1.5 分钟来执行(使用 azure 门户的查询性能洞察工具来找到它)。随着时间的推移逐行注释和测试代码后,我开始知道

from od in peopleStatus.AsNoTracking().ToList()

这条线花费了很多时间(平均 55 秒)。我不能跳过转换为 List 以进一步使用。建议我应该怎么做来优化我的查询以减少我的整体周转时间。

克里希那君·巴诺特

最后,通过删除AsNoTracking().ToList(),我将查询执行时间从 55 秒减少到平均 4.5 秒

执行时间过长的旧查询。

  var onlineData = from od in peopleStatuc.AsNoTracking().ToList()

新查询使我的总周转时间大幅减少。

  var onlineData = from od in peopleStats

我发现在执行子查询时,我不必要地将结果转换为列表(将结果转换为列表的时间随着记录的增加而增加),因此将其删除。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章