不是封闭类 Java
Posted
技术标签:
【中文标题】不是封闭类 Java【英文标题】:Is not an enclosing class Java 【发布时间】:2013-12-13 16:48:36 【问题描述】:我正在尝试制作俄罗斯方块游戏,但出现编译器错误
Shape is not an enclosing class
当我尝试创建一个对象时
public class Test
public static void main(String[] args)
Shape s = new Shapes.ZShape();
我正在为每个形状使用内部类。这是我的部分代码
public class Shapes
class AShape
class ZShape
我做错了什么?
【问题讨论】:
new Shape().new ZShape();
。 ZShape
类需要一个封闭的实例来实例化。
将内部类移动到单独的文件中
@Dimmduh 评论应该是这种情况下的答案。它们不应该是内部类。移动它们将确定存在的 Shape 类的其他问题。
这里不回答这个问题,但我可以建议在AShape
和ZShape
扩展基类Shapes
的地方使用inheritance。对于这个问题,嵌套类并不是一个很好的设计。
【参考方案1】:
ZShape
不是静态的,因此它需要外部类的实例。
如果可以的话,最简单的解决方案是制作 ZShape 和任何嵌套类 static
。
我也可以创建任何字段 final
或 static final
。
【讨论】:
制作ZShape
static
完全违背了他试图做的事情的目的,即实例化ZShape
的副本。
@Cardano 让 static
变得更容易,而不是更难。
另一个简单的解决方案是让封闭类实例化内部类,即以这种方式获取 ZShape:ZShape myShape = new Shape().instantiateZShape();
。这意味着如果没有 Shape,您获得的 ZShape 就不存在,这就是这里的意图。
@Peter Lawrey 您是如何意识到所有 Shape 实例都必须使用相同的 ZShape 的?我不是从他的消息来源那里得到的。
如果我们想要静态或实例,有两种情况。将其设为静态并不总是有帮助。【参考方案2】:
假设 RetailerProfileModel 是您的 Main 类,RetailerPaymentModel 是其中的一个内部类。可以在类外创建Inner类的对象,如下:
RetailerProfileModel.RetailerPaymentModel paymentModel
= new RetailerProfileModel().new RetailerPaymentModel();
【讨论】:
这个答案真的很有帮助,我从来不知道你可以连续调用 new 两次(而且我已经做了 8 年以上的 java!) 您当然可以多次调用 new 运算符,直到您不想保留对该对象的引用。 如果内部类的对象是这样创建的,它如何访问外部类的成员? 在内部类本身中,您可以使用 OuterClass.this。我认为没有办法从内部类的代码外部获取实例。当然,你总是可以引入自己的属性: public OuterClass getOuter() return OuterClass.this; 虽然这个语法很复杂,让我很难过,但这应该是公认的答案。【参考方案3】:我建议不要将非静态类转换为静态类,因为在这种情况下,您的内部类无法访问外部类的非静态成员。
例子:
class Outer
class Inner
//...
因此,在这种情况下,您可以执行以下操作:
Outer o = new Outer();
Outer.Inner obj = o.new Inner();
【讨论】:
那么Outer.Inner obj = (new Outer).new Inner(); @HussainKMRBehestee,不,这肯定行不通。但是,这会工作Outer.Inner obj = new Outer().new Inner();
但是阿米特,它对我有用。如果你能解释为什么它不应该工作,我会很高兴。
@HussainKMRBehestee,解释:我只能猜测Java中的语法说要实例化一个类,我们需要调用构造函数,而调用构造函数()
是强制性的。但是,C、C++ 不是必须的。 Here 是一个不起作用的例子。此外,我发现了这个post。这解释了更多关于 Java 中的语法以及它们是如何被解析的。当这种语法对您有用时,我很乐意看到一个示例案例。
哦,我的错,这是一个错字,Outer.Inner obj = (new Outer()).new Inner();希望这次没问题,感谢您注意到这一点。【参考方案4】:
如docs中所述:
OuterClass.InnerClass innerObject = outerObject.new InnerClass();
【讨论】:
虽然此链接可能会回答问题,但最好在此处包含答案的基本部分并提供链接以供参考。如果链接页面发生更改,仅链接答案可能会失效。 - From Review 谢谢!刚刚开始。【参考方案5】:有时,我们需要创建一个不能是静态的内部类的新实例,因为它依赖于父类的一些全局变量。在这种情况下,如果您尝试创建非静态内部类的实例,则会引发 not an enclosing class
错误。
以问题为例,如果ZShape
不能是静态的,因为它需要Shape
类的全局变量怎么办?
如何创建ZShape
的新实例?方法如下:
在父类中添加getter:
public ZShape getNewZShape()
return new ZShape();
像这样访问它:
Shape ss = new Shape();
ZShape s = ss.getNewZShape();
【讨论】:
【参考方案6】:Shape shape = new Shape();
Shape.ZShape zshape = shape.new ZShape();
【讨论】:
【参考方案7】:我也遇到了同样的问题。 我通过为每个内部公共类创建一个实例来解决。 至于你的情况,我建议你使用内部类以外的继承。
public class Shape
private String shape;
public ZShape zShpae;
public SShape sShape;
public Shape()
int[][] coords = noShapeCoords;
shape = "NoShape";
zShape = new ZShape();
sShape = new SShape();
class ZShape
int[][] coords = zShapeCoords;
String shape = "ZShape";
class SShape
int[][] coords = sShapeCoords;
String shape = "SShape";
//etc
然后你可以 new Shape(); 并通过shape.zShape访问ZShape;
【讨论】:
一个错误的解决方案。逻辑错误。如果内部类(例如 ZShape)需要设置任何字段,则必须在外部类的构造函数中获取它! public Shape(String field1_innerClass, int field2_innerClass...)zShape = new ZShape(String field1_innerClass, int field2_innerClass...)...【参考方案8】:不需要将嵌套类设为静态,但必须是公共的
public class Test
public static void main(String[] args)
Shape shape = new Shape();
Shape s = shape.new Shape.ZShape();
【讨论】:
【参考方案9】:在阅读接受的答案时,我起初没有意识到的一件事是,将内部类设为静态基本上与将其移动到自己的单独类中相同。
因此,当得到错误时
xxx 不是封闭类
您可以通过以下任一方式解决:
将static
关键字添加到内部类,或者
将其移到自己的单独类中。
【讨论】:
【参考方案10】:如果父类是单例,请使用以下方式:
Parent.Child childObject = (Parent.getInstance()).new Child();
getInstance()
将返回父类单例对象。
【讨论】:
【参考方案11】:为了达到问题的要求,我们可以将类放入接口中:
public interface Shapes
class AShape
class ZShape
然后像作者之前尝试过的那样使用:
public class Test
public static void main(String[] args)
Shape s = new Shapes.ZShape();
如果我们寻找合适的“逻辑”解决方案,应该使用fabric
设计模式
【讨论】:
以上是关于不是封闭类 Java的主要内容,如果未能解决你的问题,请参考以下文章