我有一个Activity
模型可以从 7 种左右不同类型的模型中提取模型。这些模型也有它们的关系,活动提要需要能够显示我想要的信息。这意味着我的查询中有大约 20 个包含。我只做了 8 个月左右的时间,而且我已经阅读了有关编译查询、存储过程以及所有这些内容可能会杀死我的内容。我还读到我可以将我的代码优先模型更改为virtual
它可以进行延迟加载,但我担心如果我有大量用户,所有这些数据库调用都会杀死我的网站。
首先是模型
public class Activity
{
public int ActivityID { get; set; }
public int ActivityTypeID { get; set; }
public int ContributorID { get; set; }
public int UserID { get; set; }
public int? ProjectID { get; set; }
public int? ProjectDocID { get; set; }
public int? CommentID { get; set; }
public int? BookID { get; set; }
public int? BookReviewID { get; set; }
public DateTime DateCreated { get; set; }
public Comment Comment { get; set; }
public ProjectDoc ProjectDoc { get; set; }
public Project Project { get; set; }
public Book Book { get; set; }
public BookReview BookReview { get; set; }
public ActivityType ActivityType { get; set; }
[ForeignKey("ContributorID")]
public User Contributor { get; set; }
[ForeignKey("UserID")]
public User User { get; set; }
public ICollection<ActivityLike> ActivityLike { get; set; }
public ICollection<ActivityComment> ActivityComment { get; set; }
}
现在查询
var activity = db.Activities
.Include(i => i.Contributor.BookStatus)
.Include(i => i.ActivityType)
.Include(i => i.ActivityLike.Select(y => y.User))
.Include(i => i.ActivityComment.Select(y => y.User))
.Include(i => i.Project.ProjectFollower)
.Include(i => i.Project.View)
.Include(i => i.Project.ProjectType)
.Include(i => i.Project.User)
.Include(i => i.Project.ProjectTag.Select(v => v.Tag))
.Include(i => i.Project.ProjectCategory.Select(v => v.Category))
.Include(i => i.Project.ProjectCharacteristic.Select(v => v.Characteristic))
.Include(i => i.Project.ProjectDoc.Select(v => v.ProjectDocVote))
.Include(i => i.Project.ProjectDoc.Select(v => v.User))
.Include(i => i.Comment.User)
.Include(i => i.Book.Author)
.Include(i => i.Book.BookReview.Select(v => v.User))
.Include(i => i.Book.BookReview.Select(v => v.BookReviewVote))
.Include(i => i.Book.BookCharacteristic.Select(v => v.Characteristic))
.Include(i => i.Contributor.Followers)
.Where(u =>
u.Contributor.Followers.FirstOrDefault(x => x.FollowerID == WebSecurity.CurrentUserId) != null
)
.OrderByDescending(d => d.DateCreated)
.Skip(offset)
.Take(results)
.ToList();
这最终就像 6600 行 SQL(或任何它)。
第一次运行需要 10-16 秒。而且因为我正在使用Skip()
jquery 并无限滚动,所以第一次每次调用 ajax 需要 10-12 秒。因此,如果我每次得到 10 个结果并且有 100 个结果,那么等待时间超过 100 秒,这太糟糕了。现在,下次用户在短时间内访问该页面时,速度非常快。
那么我应该如何改进此查询,您能否具体提供如何改进并解释解决方案,因为我很难理解已编译的查询以及其他问题。我能够做到这一点的唯一原因是因为 EF 让它变得简单……这显然是有代价的。
请原谅和滥用的术语。