为啥从 Realm DB 加载图像时 SwiftUI List 会崩溃? RAM 达到极限

Posted

技术标签:

【中文标题】为啥从 Realm DB 加载图像时 SwiftUI List 会崩溃? RAM 达到极限【英文标题】:Why SwiftUI List crashes when loading images from Realm DB? RAM reaches limit为什么从 Realm DB 加载图像时 SwiftUI List 会崩溃? RAM 达到极限 【发布时间】:2021-10-17 20:44:03 【问题描述】:

我已将大约 7000 张图像保存到 Realm DB 中,以便可以离线查看。除了加载很长的 SwiftUI 列表外,该应用程序运行良好。我相信当用户向下滚动时,所有图像都存储在 RAM 上,因为在测试时我实际上可以看到 RAM 增加。问题是,如果列表中有足够的图像,RAM 就会满并且应用程序崩溃。

他们声称 SwiftUI List 就像 UITableView 可重复使用的单元格,那么它为什么不为 list 中过去的图像释放内存呢?

List(searchResults(results: results), id: \.self)  product in 
ScrollView(.horizontal) 
            HStack
                ForEach(0...imageListGetter().count - 1, id: \.self) i in
                    
                    imageListGetter()[i]
                

//each image is added like this to the list, they are stored as Data into Realm DB and then passed as uiImage to SwiftUI Image

imageList.append(Image(uiImage: UIImage(data: imageLocation1.data!)!)

我将图像作为数据保存到领域,并将它们作为 uiImage 加载到图像视图。

任何帮助将不胜感激。

【问题讨论】:

欢迎来到 Stack Overflow!我们无法用所提供的信息真正回答您的问题。请参阅:How do I ask a good question? 和 How to create a Minimal, Reproducible Example。 Realm 对象是延迟加载的,这意味着成千上万个对象占用的 RAM 空间很小。但是,投射或存储在数组中会失去这种优势,因此它们都会吞噬内存,压倒设备。请参阅我对this question 的回答。一种选择是不转换或存储在数组中,而是使用结果作为数据源。另一种选择是使用分页并一次加载少量数据。 哦,Realm 通常不是图像存储的最佳解决方案;缩略图(几百 Kb)还可以。您的数据大小不清楚,但我想我会提到它。 Jay 先生,你又是对的!我摆脱了将结果投射到数组中,瞧!不再有 RAM 崩溃。另一方面,我将 7000 多张图像保存到一个领域,平均每张图像 500kb,而且效果很好。比使用 CoreData 的 FileManager 快得多。无论如何,再次感谢您的帮助。干杯 【参考方案1】:

Realm 对象是延迟加载的,这意味着成千上万个对象占用的 RAM 空间很小。

但是,将这些对象转换为数组或将这些对象存储在数组中会失去这一优势,因此它们都会占用内存,使设备不堪重负。

请参阅我对this question 的回复以了解更多信息

有几个解决方案。

一种选择是不将领域对象转换或存储在数组中,而是使用结果作为数据源。

如果您必须将数据存储在数组中,另一种选择是使用分页并一次加载较少量的数据。

第一个选项有很多优点,所以我建议将对象保留在 Results 对象中 - 它的行为非常类似于数组,因此我可以成为 tableViews 等的出色数据源。

【讨论】:

以上是关于为啥从 Realm DB 加载图像时 SwiftUI List 会崩溃? RAM 达到极限的主要内容,如果未能解决你的问题,请参考以下文章

为啥我无法加载位于资产目录中的图像?

为啥 Glide 只第二次加载图像? (安卓)

使用插入不工作在Realm DB中添加列表?

为啥这两种将图像从 SQL CE 加载到 WPF 图像中的方法会产生不同的结果?

为啥图片加载不出来?

无法从设备上的“文档”目录加载图像