问题的上下文
在实体框架核心,我有两个模型:CreatorPost
&Like
。每个帖子可以有无限个赞,但每个赞只属于一个帖子;一对多关系:
public class CreatorPost
{
...
}
public class Like
{
...
public CreatorPost CreatorPost { get; set; }
}
在帖子的显示中,我通过这种方式获得他们的点赞数:
int likes = _context.Likes.Where (l => l.CreatorPost == creatorPost).Count ();
由于所有帖子的点赞都存储在一个表中,所以一段时间后,当它们变得更多时,查询点赞数将花费更长的时间&更长。
的解决方案我尝试的解决方案是在CreatorPost
中添加另一列,这是一个保存喜欢计数的整数:
public class CreatorPost
{
...
public uint Likes { get; set; } // Added this
}
然后,当我想获得一个帖子的点赞数时,我只检索这个值,而不是查询所有的点赞数。在LikeCreatorPost ()
方法中,它用于向数据库添加喜欢,我添加了一段代码来向Likes
属性添加一个。
到目前为止,获得喜欢的计数是可以的,但在LikeCreatorPost ()
方法中,我想确保用户不能点赞两次,我仍然需要查询所有的喜欢并检查。
我知道缓存页面也是可能的,但我的问题是向数据库添加另一列而不是查询所有的喜欢可以提高应用程序的性能(因为添加一列会使数据库更大并影响性能)?这值得吗?有没有更好的办法让它更有效率?
你是对的,按需计算在大型数据集上可能会成为一个问题。然而,有几个选择可以帮助解决这个问题。方法取决于您的特定系统。以下是其中的一些。
- 向模型添加额外的列不是问题。但是,您应该稍微修改一下您的模型,以便它负责计算本身(领域驱动设计)。使用这种方法,计算的字段总是反映正确的点赞数。
public class CreatorPost
{
private IList<Like> likes = // initialize
public IEnumerable<Like> Likes => likes;
public uint LikeCount { get; private set; }
public void AddLike()
{
likes.Add(new Like(this, ...));
LikeCount++;
}
public void RemoveLike(...)
{
var like = likes.Where(...);
likes.Remove(like);
LikeCount--;
}
}
public class Like
{
public Like(CreatorPost post, ...)
{
CreatorPost = post;
// initialize other properties
}
public CreatorPost CreatorPost { get; init; }
}
- 在数据库中创建一个视图,以便该视图有一个计算列,汇总喜欢的数量。然后,将视图映射到CreatorPost类。使用这种方法,CreatorPost总是获得正确的喜欢数,而无需对数据库进行额外的查询。但是,请记住,表应该在过滤后的列上正确地建立索引。