访问内部类中的字段的建议/正确方法是什么?

时间:2015-05-12 19:56:04

标签: java inner-classes

假设我们有这个类及其内部类:

/* Outer.java */
public class Outer {
    private static class Inner {
        private final Object foo;

        public Inner(Object foo) {
            this.foo = foo;
        }

        public Object getFoo() {
            return foo;
        }
    }

    Inner inner = parse(/* someMistery */);

    // Question: to access foo, which is recommended?
    Object bar = inner.getFoo();
    Object baz = inner.foo;
}

我很惊讶inner.foo有效。

由于fooprivate,因此只能通过getFoo()访问 ,对吧?

2 个答案:

答案 0 :(得分:11)

  

由于foo是私有的,因此只能通过getFoo()访问,对吧?

在这种情况下,Outer也可以访问它,因为InnerOuter的成员。

6.6.1说:

  

[If]成员或构造函数被声明为private,[当时]允许访问,当且仅当它出现在顶层类主体内时才包含声明成员或构造函数。

请注意,它被指定为可以在包含声明的顶级类的主体内访问。

这意味着,例如:

class Outer {
    static class Foo {
        private Foo() {}
        private int i;
    }
    static class Bar {{
        // Bar has access to Foo's
        // private members too
        new Foo().i = 2;
    }}
}

是否使用吸气剂确实是一种品味问题。这里重要的实现是外部类可以访问其嵌套类的私有成员。

作为推荐,我个人会说:

  • 如果嵌套类是private(只有外部类可以访问它),除非getter进行计算,否则我甚至不会给它一个getter。它是任意的,其他人可以出现并选择不使用它。如果样式混合,则代码具有模糊性。 (inner.fooinner.getFoo()真的做同样的事吗?我们不得不浪费时间检查一下Inner课程。)
  • 但如果这是你喜欢的风格,你可以通过一个吸气剂。
  • 如果嵌套类不是private,请使用getter以使样式统一。

如果你真的想要隐藏private成员,即使是外部类,你可以使用本地或匿名类的工厂:

interface Nested {
    Object getFoo();
}

static Nested newNested(Object foo) {
    // NestedImpl has method scope,
    // so the outer class can't refer to it by name
    // e.g. even to cast to it
    class NestedImpl implements Nested {
        Object foo;

        NestedImpl(Object foo) {
            this.foo = foo;
        }

        @Override
        public Object getFoo() {
            return foo;
        }
    }

    return new NestedImpl(foo);
}

作为一种迂腐的说明,您的static class Inner {}在技术上是静态嵌套类,而不是内部类class Inner {}(没有static)将是一个内部类。

这是specifically defined

  

static关键字可以修改非内部类或接口C正文中成员类型T的声明。 其效果是声明C不是内部类。

答案 1 :(得分:0)

这一切都取决于您要从哪里访问该对象的代码段。由于它是一个静态嵌套类,因此您可以从任何一种方式访问​​您的对象。请参阅此链接http://www.javatpoint.com/static-nested-class以更好地理解内部类。