Java代码内的Kotlin列表与java.util.List泛型类型

问题描述 投票:0回答:2

在将项目迁移到Kotlin时,我表现出奇怪的行为。

这是在我尝试生成匕首注射器时发生的。 Java或Dagger中的问题,某人无法从通用类型解析Kotlin List

示例:


interface CacheEntity<Result> {
  fun onResult(result: Result)
  fun getUpdatableData(): Observable<Result>
}
class CacheRepository< Result, Entity:CacheEntity<Result> >(
  val entity: Entity) {

   // do some operations with Entity
   fun doSome() {
     entity.getUpdatableData()
     entity.onResult(...)
   }
}
class UserRepository: CacheEntity<User> {
  override fun onResult(result: User) {}
  override fun getUpdatableData(): Observable<User> {}
}

现在,如果我要创建缓存的用户存储库实例,一切正常然后此代码使用匕首注入转换为应用程序

val cachedUserRepo = CacheRepository<User, UserRepository>(UserRepository())

但是!如果我试图得出数据列表

class OrdersRepository: CacheEntity<List<Order>> {
  // overrides CacheEntity methods
}

val cachedOrdersRepo = CacheRepository<List<Order>, OrdersRepository>(OrdersRepository())

一切都很好,但是在Dagger生成的Java代码中不是这样:MyComponent.java


private CacheRepository<List<Order>, OrdersRepository> cachedOrdersRepository;

构建时出错

error: type argument OrdersRepository is not within bounds of type-variable Entity
  private Provider<CachedRepository<List<Order>, OrdersRepository>> cachedOrdersRepository;
                                                              ^
  where Entity,Result are type-variables:
    Entity extends CacheEntity<Result> declared in class CacheRepository
    Result extends Object declared in class CacheRepository

Java代码包含与kotlin.collections.List不兼容的java.util.List,但是用kotlin编写的dagger模块类,并返回有效的kotlin kotlin.collections.List

@Module
object RepoModule {
  @JvmStatic
  @Provides
  fun provideCacheOrdersRepository(): CacheRepository<List<Order>, OrdersRepository> {
    return CacheRepository(OrdersRepository())
  }

}

那么,如何解决这个问题?我有几个主意,但我不喜欢这样:

  • 用Java重写dagger模块,在我转换为Kotlin之前就起作用了

  • 强制使用java.util.List,但这是一个非常糟糕的主意

java kotlin dagger-2
2个回答
1
投票

这与Kotlin列表的字节码转换和签名中添加的通配符有关,使其成为java.util.List<? extends T>而不是java.lang.List<T>

[要在不切换为逆变类型(例如MutableList)的情况下进行修复,则应在@JvmSuppressWildcards类型上使用List

例如

class OrdersRepository: CacheEntity<List<@JvmSuppressWildcards Order>>

我仅添加了完整代码的一个片段,您应该检查列表的用法并在其上使用@JvmSuppressWildcards


0
投票

[确定,我找到了快速的解决方案:使用MutableList<T>解决了此问题,并且由于未知原因它与java.util.List<T>兼容。

© www.soinside.com 2019 - 2024. All rights reserved.