Kotlin:如何将对象列表插入房间?
我正在试图在基本界面中定义常见的CRUD方法,如下所示:
interface BaseDao { @Insert(onConflict = OnConflictStrategy.REPLACE) fun create(obj: I) @Insert(onConflict = OnConflictStrategy.REPLACE) fun createAll(objects: List) @Delete fun delete(obj: I) }
Room的以下ProductDao
接口从基本接口inheritance:
@Dao interface ProductDao : BaseDao { // Specific methods }
当我编译fun createAll(objects: List)
的定义fun createAll(objects: List)
产生以下错误:
参数的types必须是用@Entity或其集合/数组注解的类。
你应该为模型类添加@Entity
注解(你应该有Dao方法的具体模型类),但是在你的界面BaseDao
使用generics。 https://developer.android.com/training/data-storage/room/defining-data.html
我有同样的问题,我相信我find了解决办法:
Kotlin不可能创建通用对象数组,所以你必须做出这样的解决方法:
@Insert(onConflict = OnConflictStrategy.REPLACE) fun create(obj: I) @Transaction fun createAll(objects: List) = objects.forEach {insert(it)}
@Transaction
交易应该使这一切都发生在一个单一的事务,所以它不应该引入任何性能问题,但我不确定这一点。
更重要的是,一个简单的:
@Insert(onConflict = OnConflictStrategy.REPLACE) fun createAll(objects: List)
只要它使用的是实物,而不是generics,它也可以起作用。
我的修复是在Java中实现BaseDao
接口,直到问题依然存在。
public interface IBaseDao { @Insert(onConflict = OnConflictStrategy.REPLACE) @WorkerThread void save(T item); @Delete @WorkerThread void delete(T item); @Delete @WorkerThread void deleteAll(List items); @Insert(onConflict = OnConflictStrategy.REPLACE) @WorkerThread void saveAll(List items); }
抽象BaseDao
在Kotlin
abstract class BaseDao : IBaseDao { @WorkerThread open fun getAll(): List = TODO("Override and place the annotation @Query. Ex: @Query(\"SELECT * FROM Model\")") @WorkerThread open fun loadAll(): LiveData> = TODO("Override and place the annotation @Query. Ex: @Query(\"SELECT * FROM Model\")") }
有用!