我正在尝试创建一个由子类定义的对象数组(我认为这是正确的术语)。我可以看到这个问题反复出现,但实施仍然存在问题。
我的代码
public class Test {
private class MyClass {
int bar = -1;
}
private static MyClass[] foo;
public static void main(String args[]) {
foo = new MyClass[1];
foo[0].bar = 0;
}
}
给出错误
线程“main”中的异常java.lang.NullPointerException。
为了使其合理化,我将其分解为最简单的术语:
public class Test {
private static int[] foo;
public static void main(String args[]) {
foo = new int[1];
foo[0] = 0;
}
}
哪个似乎有效。我只是看不出我的两个例子之间的区别。 (我知道我的第一个是没有意义的,但MyClass最终将包含更多数据。)
我很确定问题是here,并且得到了很好的回答。我想我实施了解决方案:
MyClass[] foo = new MyClass[10];
foo[0] = new MyClass();
foo[0].bar = 0;
但上面的第二行发出错误
无法访问类型为Test的封闭实例。
我确实理解ArrayList是一种前进的方式,但我正在尝试掌握基本概念。
注意 - 知道虽然对编程非常熟悉,但是Java是我第一次进入面向对象编程。
答案 0 :(得分:6)
class
MyClass
是inner class
,不是子类。可以通过创建包含内部类的类的对象来访问非静态内部类。因此,如果要访问内部类,则必须首先创建外部类的对象。您可以通过以下方式完成:
Test t = new Test();
MyClass[] foo = new MyClass[10];
foo[0] = t.new MyClass();
foo.bar = 0;
答案 1 :(得分:3)
最后遇到的问题(“没有封闭的实例”)实际上与数组无关。
尝试用以下代码替换最后一个代码块:
MyClass foo = new MyClass();
即使不涉及任何数组,您也会得到完全相同的错误消息。
这里的问题是非静态内部类具有对其外部实例的隐式引用。由于您没有外部实例(您处于静态上下文中,因此没有this
),因此无法创建MyClass
实例。
你可能不需要/想要一个内部类,可以简单地使它成为static
:
private static class MyClass
另外:您的代码使用int
而不是MyClass
的原因是int[]
拥有 int
值({{1 }}是原始类型),而int
包含 MyClass[]
引用 (MyClass
是引用类型)。
答案 2 :(得分:3)
int
合理的原因,但MyClass
没有:
来自here:
Data Type Default Value (for fields)
byte 0
short 0
int 0
long 0L
float 0.0f
double 0.0d
char '\u0000'
String (or any object) null
boolean false
初始化数组时,所有元素都采用默认值。
因此,当您初始化int[]
时,所有元素都为0,因此使用它或为其分配新值没有问题。
但是,当您初始化MyClass[]
时,所有元素都是null
,这在您尝试访问其中一个元素的成员时会出现问题。
如果你不知道为什么访问null
对象的成员不起作用,你可能需要退两步并阅读一本Java书。
附加说明:
从技术上讲,这:
int[] foo = new int[1];
foo[0] = 0;
实际上更像是这样:
MyClass[] foo = new MyClass[10];
foo[0] = new MyClass();
不
MyClass[] foo = new MyClass[10];
foo[0].bar = 0;
因为您要为元素分配新值,而不是访问元素的成员。
无法访问类型为Test的封闭实例:
其他答案非常清楚,这里有3个相关的问题:
No enclosing instance of type is accessible.
No enclosing instance of type Server is accessible
"No enclosing instance of type" error while calling method from another class in Android
答案 3 :(得分:0)
您不能在静态main
方法中使用非静态内部类。
解决方案是将MyClass
声明为private static class
。