我有两个具有2个不同变量的接口。 我创建了一个实现这两个接口的类。 现在,我想将第一个接口的列表传递给另一个类的构造函数,并使用它的属性(来自两个接口)。到目前为止,我已经成功拥有了构造函数,但找不到如何传递参数列表
interface A {
var name: String
}
interface B {
var job: String
}
class C(
override var name: String,
override var job: String
) : A, B
class D() {
private fun getList() {
val list: List<A> = arrayListOf(
C("user1", "job1"),
C("user2", "job2"),
C("user3", "job3")
)
// I want to init E() my constructor here
}
}
class E<T>(val list: List<T>) where T : A, T: B {
fun display() {
list.forEach {
println("my name is ${list.get(i).name} and I am a ${list.get(i).job}")
}
}
}
答案 0 :(得分:2)
扩展@Scrobot给出的答案。
简而言之,您无法做自己想做的事情。当您将List<A>
指定为类型时,您将忽略有关列表中的元素是否实现接口B的信息。
如果您可以做自己想做的事情,则可以很容易地通过执行以下操作来破坏代码:
class PureA : A {
override var name: String
}
val list: List<A> = arrayListOf(
C("user1", "job"),
PureA("user2")
)
// The following line will not work, and for good reason
// E(list)
如果最后一行有效,则基本上可以破坏代码。 PureA是As列表中的有效元素,但不是E的列表。
以下内容与您要完成的工作非常接近:
// Doesn't work fully
class D<T> where T: A, T: B {
private fun getList(): E<T> {
val list: List<T> = arrayListOf<T>(
C("user1", "job1"),
C("user2", "job2"),
C("user3", "job3")
)
E(list)
}
}
我看不到确定您要做什么的完整方法。我假设您想允许将来的类也实现A和B。我发现可行的唯一方法是:
interface AB : A, B
class C(
override var name: String,
override var job: String
) : AB
class D {
private fun getList() {
val list: List<AB> = arrayListOf(
C("user1", "job1"),
C("user2", "job2"),
C("user3", "job3")
)
E(list)
// I want to init E() my constructor here
}
}
这是一个非常好的解决方案,即使它为您提供了更多的接口。但这通常是非常好的:)
答案 1 :(得分:1)
如果我正确理解了您的问题,则您的代码只需进行一点改进即可解决您的问题
interface A {
var name: String
}
interface B {
var job: String
}
class C(
override var name: String,
override var job: String
) : A, B
class D {
fun getList(): E<C> = E(
arrayListOf(
C("user1", "job1"),
C("user2", "job2"),
C("user3", "job3")
)
)
}
class E<T>(val list: List<T>) where T : A, T: B {
fun display() {
// for (i in 1..10) will throw OutOfBoundsException
list.forEach {
println("my name is ${it.name} and I am a ${it.job}")
}
}
}
// to test
fun main(args: Array<String>) {
D().getList().display()
/* will prints
my name is user1 and I am a job1
my name is user2 and I am a job2
my name is user3 and I am a job3 */
}