首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >使用EF Core FAST读取数千个对象

使用EF Core FAST读取数千个对象
EN

Stack Overflow用户
提问于 2016-03-08 05:56:21
回答 3查看 2.1K关注 0票数 7

我从EF内核的SQLite中读取了40,000个小对象/行,耗时18秒,这对于我的UWP应用程序来说太长了。当发生这种情况时,单核上的CPU使用率达到100%,但磁盘读取速度约为1%。

代码语言:javascript
复制
var dataPoints =  _db.DataPoints.AsNoTracking().ToArray();

如果没有AsNoTracking(),所需的时间会更长。

DataPoint是一个具有一些基本属性的小POCO。我加载的数据总量是4.5MB。

代码语言:javascript
复制
    public class DataPointDto
    {
        [Key]
        public ulong Id { get; set; }

        [Required]
        public DateTimeOffset TimeStamp { get; set; }

        [Required]
        public bool trueTime { get; set; }

        [Required]
        public double Value { get; set; }
   }

问:有没有更好的方法来加载这么多的对象,或者我被困在这个级别的性能上了?

有趣的事实: x86需要11秒,x64需要18秒。“优化代码”减少了一秒钟。使用Async将执行时间推到30秒。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2016-03-28 02:07:39

大多数答案遵循加载较少数据的常识,但在某些情况下,例如在这里,您绝对肯定地必须加载大量实体。那么我们如何做到这一点呢?

性能不佳的原因

这个操作花这么长时间是不可避免的吗?嗯,不是的。我们只从磁盘加载了一兆字节的数据,性能低下的原因是数据被拆分到40,000个微小实体上。数据库可以处理这一点,但是实体框架似乎很难设置所有这些实体,更改跟踪等。如果我们不打算修改数据,我们可以做很多事情。

我试了三件事

原语

只加载一个属性,然后你就会得到一个原语列表。

代码语言:javascript
复制
List<double> dataPoints =  _db.DataPoints.Select(dp => dp.Value).ToList();

这绕过了通常由实体框架执行的所有实体创建。此查询耗时0.4秒,而原始查询为18秒。我们讨论的是45 (!)倍的改进。

匿名类型

当然,大多数时候我们需要的不仅仅是一个基元数组,我们可以在LINQ查询中创建新的对象。实体框架不会创建它通常会创建的实体,并且操作运行得更快。为了方便起见,我们可以使用匿名对象。

代码语言:javascript
复制
var query = db.DataPoints.Select(dp => new {Guid ID = dp.sensorID, DateTimeOffset Timestamp = dp.TimeStamp, double Value = dp.Value});

此操作需要1.2秒,而通常检索相同数量的数据需要18秒。

元组

我发现在我的例子中,使用元组而不是匿名类型略微提高了性能,以下查询的执行速度大约快了30%:

代码语言:javascript
复制
var query = db.DataPoints.Select(dp => Tuple.Create(dp.sensorID, dp.TimeStamp, dp.Value));

其他方式

  1. 您不能在LinQ查询中使用结构,因此这不是一个选项
  2. 在许多情况下,您可以将许多记录组合在一起,以减少与检索许多单独记录相关的开销。通过检索较少的较大记录,您可以提高性能。例如,在我的使用案例中,我有一些每5分钟、每周7天、每天24小时测量一次的测量结果,目前我将它们单独存储,这很愚蠢。没有人会查询不到一天的时间。我计划在我做出改变时更新这篇文章,看看性能是如何变化的。
  3. 有些人推荐使用面向对象的数据库或微对象关系映射。我也从来没有用过,所以我无可奉告。
票数 8
EN

Stack Overflow用户

发布于 2016-03-09 00:02:36

您可以使用不同的技术来加载您的所有项目。

您可以创建自己的逻辑,以便在用户滚动ListView时加载部分数据(我猜您正在使用它)。

幸运的是,UWP有一种简单的方法来完成这项技术。增量加载请参阅文档和示例

https://msdn.microsoft.com/library/windows/apps/Hh701916

票数 2
EN

Stack Overflow用户

发布于 2020-06-29 19:30:08

对2600万条记录(1个datetime,1个double,1个int)进行性能测试,EF Core 3.1.5:

接受答案中建议的

  • 匿名类型或元组=大约20秒,1.3 20

  • 结构=大约15秒,0.8 15内存
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35854862

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档