【问题标题】:Getting "Entities and POJOs must have a usable public constructor" when using Room database使用 Room 数据库时获取“实体和 POJO 必须具有可用的公共构造函数”
【发布时间】:2020-10-31 10:37:41
【问题描述】:

这似乎是一个非常常见的错误,因为我能够找到与此类似的其他问题,但无法确定问题出在哪里。

所以我有这个实体

@Entity(tableName = "story_id")
data class StoryIdEntity(
    @PrimaryKey
    @ColumnInfo(name = "type")
    val type: String,
    @ColumnInfo(name = "ids")
    val ids: List<Int>
)

我有这个 Dao 接口

@Dao
interface HackerNewsDaoInterface {
    @Query("SELECT ids FROM story_id where type = :type")
    suspend fun getStories(type: String): List<Int>
}

当我编译这个时,我收到以下错误。

  • 实体和 POJO 必须具有可用的公共构造函数。您可以有一个空的构造函数或一个参数与字段匹配的构造函数(按名称和类型)。
  • 查询返回一些列 [ids],这些列没有被 java.lang.Integer 使用。您可以在字段上使用 @ColumnInfo 注释来指定映射。您可以通过使用 @SuppressWarnings(RoomWarnings.CURSOR_MISMATCH) 注释方法来抑制此警告。查询返回的列:ids。 java.lang.Integer 中的字段:

B/w 我有一个功能正常的 List 类型转换器。

更新 1

我暂时把Dao的方法改了,让它生效。

@Dao
interface HackerNewsDaoInterface {
    @Query("SELECT * FROM story_id where type = :type")
    suspend fun getStories(type: String): StoryIdEntity
}

【问题讨论】:

    标签: android kotlin android-room


    【解决方案1】:

    为id列表创建一个包装类,例如:

    data class StoryIds (
        val ids: List<Int>
    )
    

    然后修改您的查询以返回包装类的实例:

    @Query("SELECT ids FROM story_id where type = :type")
    suspend fun getStories(type: String): StoryIds
    

    【讨论】:

    • 你不觉得这个包装类是多余的吗?直接访问列表有什么问题。我相信您的解决方案会奏效,但我的方法有什么问题?
    • 我可以通过实验和查看 Room 生成的代码确定,当前版本的 Room 不支持这种类型的查询。我在related answer 中提供了一些解释。
    • 嗯,太糟糕了。此时,我可以返回 StoryIdEntity 本身而不是包装器 ??‍♂️。
    【解决方案2】:

    将此添加到您的数据类以修复“必须具有可用的公共构造函数”

    constructor():this("", ArrayList<Int>())
    

    【讨论】:

      猜你喜欢
      • 2020-09-03
      • 2021-05-01
      • 2021-12-25
      • 2018-06-24
      • 1970-01-01
      • 2017-11-20
      • 2019-05-21
      • 1970-01-01
      • 2020-08-12
      相关资源
      最近更新 更多