已经关联了一个开放的数据读取器

本文关键字:数据 读取 一个 关联 | 更新日期: 2023-09-27 18:16:09

我正在制作这个自动完成搜索栏,其中包含标题,描述和category_id,但我需要类别名称,这是在另一个表中,所以我从我的广告表中取出类别id,并检查id与类别中的表,我知道我需要关闭连接到数据库之前,我可以做一个新的,所以我需要另一种方式。

public class SetGetAds
    {
        public string Title { get; set; }
        public string Description { get; set; }
        public string Category { get; set; }
    }
using (var db = new myProjectEnt())
        {
            var getAds = (from a in db.ads where a.title.Contains(searchQuery) select new { a.title, a.description, a.categories_id }).Take(15);
            var ads = new List<SetGetAds>();
            foreach (var setAds in getAds)
            {
                var getCategory = (from c in db.ads where c.title.Equals(setAds.categories_id) select new { c.title }).SingleOrDefault();
                ads.Add(new SetGetAds { Title = setAds.title, Description = setAds.description, Category = getCategory.title });
                var jsonString = new JavaScriptSerializer();
                return jsonString.Serialize(ads);
            }
        }

已经关联了一个开放的数据读取器

getAds是一个可枚举序列,它从读取器惰性地获取数据-然后循环遍历它。然后,对于要执行第二个查询的每个 <getCategory。这里重要的是getAds>仍在读取数据 -所以是的,您有嵌套命令。

选项(按优先顺序排列,最高=首选):

  • 重新构造查询以同时获得类别,一次性避免嵌套查询和明显的N+1问题
  • getAds后面加一个.ToList(),急切完成第一个查询
  • 启用MARS,以便允许嵌套查询

N+1问题通常是性能问题的根源;就我个人而言,我希望以避免这种情况的方式编写此查询,例如:

var ads = (from a in db.ads
           where a.title.StartsWith(searchQuery)
           join c in db.ads on a.categories_id equals c.title
           select new { a.title, a.description, a.categories_id,
                       category = c.title }).Take(15);