使用实体框架最大化性能 [重复]
Posted
技术标签:
【中文标题】使用实体框架最大化性能 [重复]【英文标题】:Maximizing Performance with the Entity Framework [duplicate] 【发布时间】:2015-12-17 15:51:48 【问题描述】:我正在开发旅游网站。 当用户输入位置进行搜索(自动完成)时,我的操作会返回所有城市,即城市区域、地区、地区翻译、酒店......从用户输入开始
我首先使用实体代码。但它的响应时间太长了。我该如何优化呢?如何减少时间?
public JsonResult AutoComplateCityxxxxxxxx(string culture, string q)
List<Tuple<string, int, int>> result = new List<Tuple<string, int, int>>();
using (var db = new TourismContext())
ModelState.Remove(q);
var query = SearchWordFunctions.WordFunctions(q);
var ListCity = db.CityTranslations.Where(
c => (c.Slug.StartsWith(query) || c.Name.StartsWith(query))
&&
c.City.Latitude.HasValue
).GroupBy(x => x.CityID).Select(g => g.FirstOrDefault()).Take(10);
var ListRegion = db.RegionTranslations.Where(
r => (r.Slug.StartsWith(query) || r.Name.StartsWith(query))
&&
r.Region.Latitude.HasValue
&&
r.Region.RefID == 0 && r.Region.IsShow > 0
).GroupBy(x => x.RegionID).Select(g => g.FirstOrDefault()).Take(10);
var LandMark = db.CityLandMarks.Where(l => l.Translations.Any(t => t.Name.StartsWith(query)) && l.Latitude.HasValue).Take(10);
var hotel = db.HotelTranslations.Where(t => t.Url.Contains(query) && t.Hotel.Status > 0 && t.Culture.Code == culture).ToList();
result.Clear();
foreach (var item in ListCity.OrderBy(o => o.Name.Length))
result.Add(new Tuple<string, int, int>(string.Concat(item.Name, " - <b>", item.City.Country.Translations.Single(t => t.CultureID == 1).Name, "<b>"), item.CityID, 1));
if (db.Regions.Any(r => r.CityID == item.CityID))
var regions = db.Regions.Where(r => r.CityID == item.CityID && r.Latitude.HasValue && r.RefID == 0 && r.IsShow > 0).GroupBy(g => g.ID).Select(x => x.FirstOrDefault()).ToList().OrderByDescending(o => o.SearchRating).Take(10);
foreach (var regItem in regions)
result.Add(new Tuple<string, int, int>(string.Concat(regItem.Translations.FirstOrDefault().Name, " - <b>", item.Name, "</b> - <b>", regItem.City.Country.Translations.FirstOrDefault().Name, "<b>"), regItem.ID, 2));
if (ListCity.Count() <= 0)
foreach (var item in ListRegion)
result.Add(new Tuple<string, int, int>(string.Concat(item.Name, " - <b>", item.Region.City.Translations.Single(t => t.Culture.Code == culture).Name, "</b> - <b>", item.Region.City.Country.Translations.Single(t => t.Culture.Code == culture).Name, "</b>"), item.RegionID, 2));
foreach (var item in LandMark)
result.Add(new Tuple<string, int, int>(string.Concat(item.Translations.FirstOrDefault().Name, " - <b>", item.City.Translations.FirstOrDefault().Name, "</b> - <b>", item.City.Country.Translations.FirstOrDefault().Name, "</b>"), item.ID, 3));
foreach (var item in hotel)
result.Add(new Tuple<string, int, int>(string.Concat(item.Name, " - <b class=\"refid\" data=\"" + item.HotelID + "\">", item.Hotel.Region.City.Translations.First().Name, "</b>"), item.Hotel.Region.CityID, 1));
return Json(result, JsonRequestBehavior.AllowGet);
【问题讨论】:
【参考方案1】:如果没有看到您生成的数据库架构或对数据库引擎或服务器配置一无所知,就很难确定什么会最大程度地提高您的查询性能。不过,在查看您的代码时,我建议确保以下属性具有与之关联的索引:
CityTranslations.Slug
CityTranslations.Name
RegionTranslations.Slug
RegionTranslations.Name
CityLandmarks.Name
这应该会给您带来立竿见影的效果,因为 StartsWith 应该生成 LIKE 'xxx%'
形式的子句,因此索引应该会显着提高性能。
HotelTranslations
可能需要在某种程度上重新访问,因为 Contains 会生成 LIKE '%xxx%'
形式的子句,这不会从简单的索引中受益。
如果这些字段上已有索引,请提供有关您的配置(数据库、服务器配置、生成的架构等)的其他信息。
【讨论】:
以上是关于使用实体框架最大化性能 [重复]的主要内容,如果未能解决你的问题,请参考以下文章
指定的密钥太长;实体框架 6 中的最大密钥长度为 767 字节 Mysql 错误