|
|
1
8
一个快速测试表明,目前是的,为内置的原始类型和结构创建了一个防御副本。 使用vs 2017编译以下代码(.net 4.5.2,c 7.2,版本构建):
使用ilspy进行反编译时生成以下结果:
(或者,如果您喜欢IL:)
|
|
|
2
4
从JIT的角度来看
Eg在
的代码
注意,因为
以及代码
如果JIT输入,这个额外的成本通常可以撤消,尽管并不总是如此。 |
|
|
3
3
对于当前的编译器,防御性拷贝似乎确实同时针对“primitive”值类型和其他非只读结构。具体来说,它们的生成方式与它们的用途类似
看看 this suite of examples . 您可以查看IL和JIT程序集。
它取决于您是否访问
不,仍将在呼叫站点为可能发生变化的成员制作防御拷贝
好吧,所有类型都是“安全的”——副本确保了这一点。我假设你在问哪种类型会避免防御性拷贝。正如我们在上面看到的,它比“参数的类型是什么”更复杂?没有单一副本:副本在某些引用中发出
目前,某些默认方法似乎被视为纯方法,编译器在这些情况下避免复制。如果我不得不猜测的话,这是预先存在的行为的结果,编译器使用了一些最初为开发的“只读”引用的概念。
也就是说,既然只读引用可能会变得更常见,那么可以调用的方法的“白名单”就可以了。 没有 防御性拷贝可能会在未来增长。目前,这似乎有些武断。 |
|
|
4
1
没有什么,
老实说,文档可能会更清晰一点;readonly在这个上下文中是一个令人困惑的术语,它应该简单地说类型应该是不可变的。 没有规则知道任何给定的类型是否是不可变的;只有仔细检查API才能给出一个想法,或者,如果幸运的话,文档可能会说明它是不是不变的。 |