C# 在ML.NET中延迟加载位图

C# 在ML.NET中延迟加载位图,c#,ml.net,C#,Ml.net,我在ML.NET图像分类中找到的所有示例都是在训练管道时使用图像路径的,然而,在生产过程中。我想直接从位图进行预测,因此我将学习管道转换为使用位图而不是路径。这会导致其他问题,例如当我们在内存中加载了615.000位图的IEnumerable数据集列表时,这台电脑没有足够的RAM 当管道进行拟合/训练时,是否有方法创建包含位图模型的延迟加载IEnumerable数据集 编辑: 根据JonasH的建议,我只是实现自己的枚举器来处理在运行时加载图像。以下是实施方案: public class Ima

我在ML.NET图像分类中找到的所有示例都是在训练管道时使用图像路径的,然而,在生产过程中。我想直接从位图进行预测,因此我将学习管道转换为使用位图而不是路径。这会导致其他问题,例如当我们在内存中加载了615.000位图的IEnumerable数据集列表时,这台电脑没有足够的RAM

当管道进行拟合/训练时,是否有方法创建包含位图模型的延迟加载IEnumerable数据集

编辑:

根据JonasH的建议,我只是实现自己的枚举器来处理在运行时加载图像。以下是实施方案:

public class ImageDataCollection : IEnumerable<ImageClassificationData>
{
    private IEnumerable<string> files { get; set; }
    public Func<Bitmap, Bitmap> Handler { get; set; }

    public ImageDataCollection(IEnumerable<string> files)
    {
        this.files = files;
    }

    public IEnumerator<ImageClassificationData> GetEnumerator()
    {
        IEnumerator<string> iterator = files.GetEnumerator();
        while (iterator.MoveNext())
        {
            string data = iterator.Current;
            Bitmap image = new Bitmap(data);
            if (Handler != null)
            {
                image = Handler(image);
            }
            string[] c = data.Split(new char[] { '\\' });
            yield return new ImageClassificationData { Label = c[c.Length - 1], Image = image };
            image.Dispose();
        }
    }

    IEnumerator IEnumerable.GetEnumerator()
    {
        return this.GetEnumerator();
    }
}
公共类ImageDataCollection:IEnumerable
{
私有IEnumerable文件{get;set;}
公共函数处理程序{get;set;}
公共ImageDataCollection(IEnumerable文件)
{
this.files=文件;
}
公共IEnumerator GetEnumerator()
{
IEnumerator迭代器=files.GetEnumerator();
while(iterator.MoveNext())
{
字符串数据=迭代器.Current;
位图图像=新位图(数据);
if(处理程序!=null)
{
image=Handler(image);
}
字符串[]c=data.Split(新字符[]{'\\'});
返回新的ImageClassificationData{Label=c[c.Length-1],Image=Image};
image.Dispose();
}
}
IEnumerator IEnumerable.GetEnumerator()
{
返回此.GetEnumerator();
}
}

这个有效但是我想把它看作是ML.NET中某种类型的扩展方法,如果可能的话,或者至少是有文档记录的,因为这并不清楚,深度学习毕竟使用了很多RAM:p..

Linq语句是惰性评估的。因此,如果您有一个路径列表,并使用select语句加载位图,则应该延迟加载位图,除非管道使用.ToList()或类似语句将IEnumerable具体化


但是,位图使用非托管内存进行存储,除非您希望依靠终结器释放内存,否则应将其释放。您也许可以使用生成位图然后对其进行处理的方法,但如果框架在迭代之间保留引用(例如在并行循环中),则此方法可能会失败。

幸运的是,他们似乎没有在内部将其强制转换为列表,因此它确实有效。奇怪的是,微软的“深度”学习库并没有更好地记录大数据集场景:PHA您是否想过不实现自己的IEnumerable,而是实现自己的IDataView?它是为了支持。下面是[LoadFromEnumerable]()使用的实现。Theodor,我一直在尝试修改我的管道以使用内存中的位图,但到目前为止都是空手而归。不要以为你能提供你最终得到的管道或者一个指向你学会如何改变它的指针?谢谢