java – 具有自我约束的泛型的私有访问
发布时间:2020-12-15 08:43:17 所属栏目:Java 来源:网络整理
导读:将私有字段访问与 Java中的 CRTP相结合似乎在可见性规则中发现了一个奇怪的边缘情况: public abstract class TestO extends TestO implements Cloneable { private int x = 0; @SuppressWarnings("unchecked") @Override protected final O clone() { try {
将私有字段访问与
Java中的
CRTP相结合似乎在可见性规则中发现了一个奇怪的边缘情况:
public abstract class Test<O extends Test<O>> implements Cloneable { private int x = 0; @SuppressWarnings("unchecked") @Override protected final O clone() { try { return (O) super.clone(); } catch (CloneNotSupportedException ex) { throw new AssertionError(ex); } } public final int getX() { return x; } public final O withX(int x) { O created = clone(); created.x = x; // Compiler error: The field Test<O>.x is not visible return created; } } 只需将withX()方法更改为此… public final O withX(int x) { O created = clone(); Test<O> temp = created; temp.x = x; return created; } …使代码编译.我在Oracle的javac和Eclipse的编译器中对此进行了测试.是什么赋予了? 解决方法
这实际上不是泛型的问题.
JLS inheritance rules使私有字段在子类中不可见.因为X是私有的,所以它不是类型O的成员,即使它是Test< O>类型的成员. O是Test< O>的子类型.如果您使用过以下代码:
public final O withX(int x) { Test<O> created = clone(); created.x = x; return (O) created; } 它会工作.这是Java不支持LSP的实例,但它只是类型系统的本地问题,因为私有字段仅可用于相同类型的对象.如果它不起作用,那么私有字段就不会私有.我不认为对递归模板的规则有一个特殊的例外是一个好主意. 请注意,这实际上并不是对您可以做的限制.您可以随时将子类型转换为超类型,以便进行更改,就像在替代代码中一样. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |