了解C#中的延迟加载优化 [英] Understanding lazy loading optimization in C#

查看:298
本文介绍了了解C#中的延迟加载优化的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在阅读了一些yield的方式之后,foreach,linq推迟了执行和迭代器在C#中的工作.我决定尝试在一个小项目中优化基于属性的验证机制.结果:

After reading a bit of how yield, foreach, linq deferred execution and iterators work in C#. I decided to give it a try optimizing an attribute based validation mechanic inside a small project. The result:

private IEnumerable<string> GetPropertyErrors(PropertyInfo property)
{
    // where Entity is the current object instance
    string propertyValue = property.GetValue(Entity)?.ToString();

    foreach (var attribute in property.GetCustomAttributes().OfType<ValidationAttribute>())
    {
        if (!attribute.IsValid(propertyValue))
        {
            yield return $"Error: {property.Name} {attribute.ErrorMessage}";
        }
    }
}

// inside another method
foreach(string error in GetPropertyErrors(property))
{
    // Some display/insert log operation
}

我发现这很慢,但这可能是由于反射或要处理的大量属性造成的.

I find this slow but that also could be due to reflection or a large amount of properties to process.

所以我的问题是... 这是延迟加载机制的最佳选择还是很好的利用?还是我丢失了某些东西,只是在浪费大量的资源.

So my question is... Is this optimal or a good use of the lazy loading mechanic? or I'm missing something and just wasting tons of resources.

注意:代码意图本身并不重要,我担心的是在其中使用延迟加载.

NOTE: The code intention itself is not important, my concern is the use of lazy loading in it.

推荐答案

延迟加载不是C#或实体框架特有的内容.这是一种常见的模式,它允许延迟一些数据加载.延迟表示不立即加载.某些需要的示例:

Lazy loading is not something specific to C# or to Entity Framework. It's a common pattern, which allows defer some data loading. Deferring means not loading immediately. Some samples when you need that:

  • 在(Word)文档中加载图像.文档可能很大,并且可以包含数千个图像.如果要在打开文档时全部加载它们,则可能会花费大量时间.没有人愿意坐下来观看30秒以加载文档. Web浏览器中使用相同的方法-资源不随页面正文一起发送.浏览器推迟了资源加载.
  • 加载对象图.它可能是数据库中的对象,文件系统对象等.加载完整图形可能等同于将所有数据库内容加载到内存中.这要花多长时间?有效率吗?否.如果您要构建一些文件系统资源管理器,您将在开始使用它之前加载系统中每个文件的信息吗?如果仅加载有关当前目录的信息(可能是直接子目录),则速度会更快.

延迟加载并不总是意味着延迟加载,直到您真正需要数据为止.在真正需要该数据之前,可能会在后台线程中进行加载.例如.您可能永远都不会滚动到网页底部来查看页脚图像.延迟加载仅意味着延迟. C#枚举器可以帮助您.考虑获取目录中的文件列表:

Lazy loading not always mean deferring loading until you really need data. Loading might occur in background thread before you really need that data. E.g. you might never scroll to the bottom of web page to see footer image. Lazy loading means only deferring. And C# enumerators can help you with that. Consider getting list of files in directory:

string[] files = Directory.GetFiles("D:");
IEnumerable<string> filesEnumerator = Directory.EnumerateFiles("D:");

第一种方法返回文件数组.这意味着目录应该获取其所有文件,并将其名称保存到数组之前,甚至可以获取第一个文件名.就像在查看文档之前先加载所有图像.

First approach returns array of files. It means directory should get all its files and save their names to array before you can get even first file name. It's like loading all images before you see document.

第二种方法使用枚举器-当您要求下一个文件名时,它将一个接一个地返回文件.这意味着立即返回枚举器,而不会获取所有文件并将其保存到某个集合中.您可以在需要时一一处理文件.此处延迟获取文件列表.

Second approach uses enumerator - it returns files one by one when you ask for next file name. It means that enumerator is returned immediately without getting all files and saving them to some collection. And you can process files one by one when you need that. Here getting files list is deferred.

但是您应该小心.如果不推迟基础操作,则返回枚举数不会给您带来任何好处.例如.

But you should be careful. If underlying operation is not deferred, then returning enumerator gives you no benefits. E.g.

public IEnumerable<string> EnumerateFiles(string path)
{
    foreach(string file in Directory.GetFiles(path))
        yield return file;
}

此处使用GetFiles方法,该方法在返回文件名之前先填充文件名数组.因此,一一生成文件不会给您带来速度上的好处.

Here you use GetFiles method which fills array of file names before returning them. So yielding files one by one gives you no speed benefits.

在您遇到的情况下,您遇到完全相同的问题-GetCustomAttributes扩展内部使用了Attribute.GetCustomAttributes方法,该方法返回属性数组.因此,您不会减少获得第一个结果的时间.

Btw in your case you have exactly same problem - GetCustomAttributes extension internally uses Attribute.GetCustomAttributes method which returns array of attributes. So you will not reduce time of getting first result.

这篇关于了解C#中的延迟加载优化的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆