(可变集合是可变的)在Kotlin中返回true [英] (imutable collection is mutable) returns true in Kotlin

查看:83
本文介绍了(可变集合是可变的)在Kotlin中返回true的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

为什么在Kotlin中会发生这种情况?

Why this is happening in Kotlin:

val list: List<Int> = listOf(1, 2, 3)// Immutable list

if(list is MutableCollection<*>){// why this "if" condition is true?
    println("is mutable")// this line is printed
    (list as MutableCollection<Int>).add(4) // this results to java.lang.UnsupportedOperationException
}

list is MutableCollection返回true,表明Kotlin不可变集合对象实现了MutableCollection接口,但是它不会更改集合中的项目,而是抛出UnsupportedOperationException

list is MutableCollection returns true that shows Kotlin Immutable collection objects implements MutableCollection interface but instead of changing items in collection it throws UnsupportedOperationException

是真的吗?如果是,为什么不可变集合对象在Kotlin中实现MutableCollection接口?

Is it true? and if yes why Immutable collection objects implement MutableCollection interface in Kotlin?

是因为Kotlin集合从Java集合继承而来,并且已经存在更改方法(添加,删除,...),并且避免更改集合的唯一方法是重写它并引发异常(即使这是真的)不需要Kotlin不可变集合对象实现MutableCollection接口,因为Java更改集合方法已经存在并且可以被覆盖)?

Is it because of Kotlin collections inherit from Java Collections and altering methods (add, remove, ...) already is there and the only way to avoid altering collection is to override it and throw an exception (even if this is true it is not necessary for Kotlin immutable collection objects to implement MutableCollection interface because java altering collection methods already are there and can be overridden)?

推荐答案

否,这不是正确的解释.这段代码应该可以帮助您了解发生了什么:

No, that's not the correct explanation. This code should help you understand what's going on:

val list: List<Int> = listOf(1, 2, 3) 

println("list class is = ${list::class.java}")

if(list is MutableCollection<*>) {
    println("is mutable") 
    (list as MutableList<Int>)[0] = 42
    println(list)
}

输出为

list class is = class java.util.Arrays$ArrayList
is mutable
[42, 2, 3]

因此,解释是listOf(1, 2, 3)返回Arrays $ ArrayList列表,即通过执行Arrays.asList(1, 2, 3)在Java中将返回的列表.这是一个可变的列表,但是您不能添加任何内容,因为它具有固定的大小,因为它由数组支持.

So, the explanation is that listOf(1, 2, 3) returns an Arrays$ArrayList list, i.e. the list that would be returned in Java by doing Arrays.asList(1, 2, 3). It is a mutable list, but you can't add anything to it, because it has a fixed size, since it's backed by an array.

科特林列表并不是真正不变的.它们只是没有任何允许对其进行突变的方法:它们只是不可变的接口,它们仅公开实际可变列表的只读方法.如果您欺骗列表并将其转换为可变列表,那么,如果该列表实际上是Java列表,则转换将成功,但是您不知道您是否真的能够对其进行突变,就像在Java中一样:一个List可以是一个不能完全变异的emptyList,或者是上面示例中的不可调整大小的列表,或者是一个完全可变的列表,例如ArrayList.

Kotlin lists aren't truly immutable. They just don't have any method allowing to mutate them: they're just immutable interfaces that only expose the readonly methods of an actually mutable list. If you cheat and cast the list to a mutable list, then, if the list is in fact a Java List, the cast will succeed, but you can't know if you're actually be able to mutate them, just like in Java: a List could be an emptyList, which can't be mutated at all, or a non-resizable list as in the above example, or a fully mutable list like an ArrayList.

这篇关于(可变集合是可变的)在Kotlin中返回true的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆