在Groovy中,集合实现之间的强制转换将复制源代码

在Groovy中,集合实现之间的强制转换将复制源代码,groovy,collections,casting,Groovy,Collections,Casting,下面的代码 void testReference() { List<String> source = new ArrayList<>() source.add("element") List reference = (ArrayList)source // all ok, creates reference as types match assertSame(source,reference) List copy

下面的代码

void testReference() {
    List<String> source = new ArrayList<>()
    source.add("element")
    List reference = (ArrayList)source // all ok, creates reference as types match
    assertSame(source,reference)
    List copyNotReference = (LinkedList)source // should fail on GroovyCastException, creates copy instead
    assertNotSame(source,copyNotReference) // this works, copy is a different object
    copyNotReference.add("second element")
    println source
    println copyNotReference
}
只有在强制转换属于集合子类型的类型时,才会发生这种行为

问题:
是什么Groovy机制导致了这种意外行为?

Groovy允许通过强制转换对象来强制对象(
asType
)。这是为集合实现的

将给定集合转换为其他类型。默认混凝土 类型用于列表、集合或分类集合。如果给定类型具有 采用集合的构造函数,该集合被使用。否则 调用被推迟到{@link#asType(Object,Class)}。如果这 集合已为给定类型,同一实例为 返回


一定是这样。通过
(CastTo)o
的标准铸造和作为CastTo的
o使用相同的机制。奇怪的是,如果您使用自定义类型
C扩展(一些Java集合类型)
则会创建自定义实例,就好像它实现了asType一样。但事实并非如此,标准集合的asType用于数据集填充。太多的神奇了!如果您不喜欢这种行为,请显式重写
asType
。否则,您将继承默认行为(这与您继承
.toString()
)的“魔力”相同),我坚持我的注释。我相信最广泛理解的强制转换特性是返回的对象引用与源相同的实例。对于Groovy,这不再适用,这让VM语言程序员感到困惑。
[element]
[element, second element]