我有一个大型树状数据结构的对象,其行为大部分相同,但在一两种方法上有所不同,这些方法计算用于导航结构的一些键。不同的行为取决于对象在结构中的位置。
我开始使用抽象基类,并有几个实现每种行为类型的子类。这给了我大约十个子类型,它们a)难以智能地命名并且b)在我的项目的源文件夹中看起来有点笨拙,因为它们非常相似。
我希望有一个工厂类可以动态地执行匿名子类的实例。这会给我很大的灵活性,并为很多很好的改进打开了大门,例如共享数据和参数化东西,在我的代码结构中看起来会更清晰。但是,整个事情对内存占用和内存访问时间非常敏感,而且我有很多这些对象。我是否必须考虑匿名课程的任何缺点或不同之处?
答案 0 :(得分:4)
与非静态内部类一样,匿名类具有对其定义的类的隐藏引用,如果使用序列化可能会导致问题,当然也会阻止外部类的对象符合GC的条件 - 但这是如果你在一个工厂类中这样做,就不会有问题。
答案 1 :(得分:3)
匿名类与命名类没有区别。
但是,有许多对象会影响你的内存占用和性能(垃圾收集)。
从你所说的,我想知道是否可以将你的课分成两部分:
变量方法:根据结构中的位置计算一些键。
答案 2 :(得分:2)
如上所述,匿名内部类通常具有对其声明的类的隐藏引用。但是,您可以通过在静态方法中声明匿名类来消除此问题(简单,并且不是很明显)。
这种技术的主要缺点是在罐子中看到的类名将被编号(如“MyClass $ 0.class”)并且在堆栈跟踪中不易识别(当然除了使用行号)和没有toString()方法在您自己的println语句中不容易识别。
声明静态内部类是一种很棒的技术。它将消除所有这些缺点,并保持您的文件层次结构紧凑。除非你需要扩展它们,否则还要考虑将这些内部类设为私有或最终。
答案 3 :(得分:1)
班级是一个班级。无论它是“顶级”类,常规内部类,本地内部类还是匿名内部类都无关紧要。
非静态内部类或访问其封闭类的私有成员的内部类将在其中包含一些额外的代码。对于非静态内部类,编译器添加一个引用封闭实例的成员变量。如果内部类访问封闭类的任何私有成员,则编译器将使用“package-private”(默认)可访问性在封闭类中合成访问器。