在Room数据库中保存图片

3

我想在我的房间数据库中保存小图片,但是有两个问题:

  1. 如何将图像保存到我的数据库中?
  2. 如何将多个图像保存到我的数据库中?

我尝试按照开发者页面推荐的方式保存位图(https://developer.android.com/training/data-storage/room/defining-data)。

@Parcelize
@Entity(tableName = "image_table")
data class ImgMod(

    @PrimaryKey(autoGenerate = true)
    var invoiceId: Long = 0L,

    @ColumnInfo(name = "image")
    var single_img: Bitmap?
): Parcelable

然而我收到了以下错误:

无法确定如何将此字段保存到数据库中。你可以考虑为它添加类型转换器。

第二,我想要在一个数据库条目中保存多张图片。但是当我使用下面的代码时,我遇到了相同的错误:

    @ColumnInfo(name = "imageList")
    var img_list: ArrayList<BitMap>

或将解码后的位图作为字符串

    @ColumnInfo(name = "imageList")
    var decoded_img_list: ArrayList<String>

非常抱歉,如果这是一个非常基础的问题。但是我该如何配置数据库/处理数据以获得图像列表?

提前感谢, rot8

1个回答

7

将位图通过 base64 编码为字符串,然后将其放入数据库行中,是一个非常简单的将图片存入数据库的方法(虽然我个人不推荐这么做)。

需要注意的是,位图非常消耗内存;而 base64 编码会增加数据大小,因此在加载大量图像时要小心...... 我认为 Room 和 SQLite 都支持二进制数据(即 blob),因此您可以将一个列声明为 ByteArray,然后它应该能够正常工作。

在我的项目中,我所做的是将图片写入应用程序的内部或外部存储中,然后将引用 Uri 作为 String 存储起来,以便以后从磁盘中检索图像。

更加不推荐的是,在一个行中存储多个值;在 SQL 中,将列表存储在一列中绝对不是您应该遵循的模式。创建一个“连接”表应该足够简单,或者只需添加一个额外的列来进行分组即可,对吧?


1
谢谢你详细的解释。:) 你说服了我,将多个值/图像存储在一个单元格中并不是一个好的做法。但是,我对在文件系统中保存图像与在数据库中保存图像有一个基本的问题。在我的具体项目中,我希望至少保存这些图像10年时间。你是否仍然建议使用文件系统?因为从我天真的观点来看,数据库似乎更安全。 - rot8
你怎么说才更安全呢?也许有些东西超出了我的理解,但是如果用户“清除应用数据”,数据库和内部文件都会被删除。如果我真的想长期保存一张图片,我会将它上传到某个在线服务器,并每天运行一个同步任务¯_(ツ)_/¯ - Some random IT boy
如果你担心用户访问这些文件,请确保使用内部存储而不是外部存储。 - Some random IT boy
是的,我计划将数据保存在服务器上,而且我觉得只有一个SQL数据库来维护比同时拥有数据库和文件服务器更整洁。谢谢你告诉我内部存储和外部存储的区别。 - rot8
1
这个问题基本上是一样的...关键问题在于,当你从数据库中提取图像时,你会提取整个图像(这会占用大量内存)。如果你使用文件系统,像Picasso和Glide这样的库在加载图像时会进行一些智能计算,并考虑到你要放置图像的图像视图的大小。它们还会进行缓存以实现更快的图像加载速度,这是使用它们的一个非常酷的好处。 - Some random IT boy

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接