2

我有一个大型的树状对象数据结构,这些对象的行为基本相同,但在计算用于在结构中导航的一些键的一种或两种方法上有所不同。不同的行为取决于对象在结构中的位置。

我从一个抽象基类开始,并有几个实现每种行为的子类。这给了我大约十个子类型,它们 a) 难以智能地命名,b) 在我的项目的源文件夹中看起来有点笨拙,因为它们都非常相似。

我更喜欢有一个工厂类来动态分配匿名子类的实例。这将给我很大的灵活性,并为许多不错的改进打开大门,例如共享数据和参数化的东西,并且在我的代码结构中看起来更清晰。然而,整个事情对内存占用和内存访问时间非常敏感,我会有很多这样的对象。我是否必须考虑匿名课程的任何缺点或特点?

4

4 回答 4

4

与非静态内部类一样,匿名类对定义它们的类有一个隐藏的引用,如果您使用序列化,这可能会导致问题,并且当然会阻止外部类的对象符合 GC 条件——但这不太可能如果您在单个工厂类中执行此操作,则会出现问题。

于 2009-10-01T15:10:14.693 回答
3

匿名类与命名类没有什么不同。

但是,是的,拥有许多对象会影响您的内存占用和性能(垃圾收集)。


根据您所说,我想知道是否可以将您的课程分成两部分:

  1. 一个类中的所有常量方法(没有此类的子类)。
  2. 所有变量方法(见后文)都封装在 Position 接口中。您可以有一些实现它的类。这些类的对象将没有状态,因此它们可以是共享实例,这对于性能和内存来说都是极好的)。

可变方法:根据结构中的位置计算一些键。

于 2009-10-01T15:09:33.103 回答
2

如前所述,匿名内部类通常具有对声明它的类的隐藏引用。但是,您可以通过在静态方法内部声明匿名类来消除这种情况(简单,而且不是很明显)。

这种技术的主要缺点是在 jars 中看到的类名将被编号(如“MyClass$0.class”)并且在堆栈跟踪中不容易识别(当然使用行号除外)并且没有 toString() 方法不容易识别在您自己的 println 语句中。

声明静态内部类是一项很棒的技术。它将消除所有这些缺点并保持文件层次结构紧凑。除非您需要扩展它们,否则还应考虑将这些内部类设为私有或最终类。

于 2009-10-01T15:35:48.893 回答
1

一个班级就是一个班级。不管是“顶级”类、常规内部类、本地内部类还是匿名内部类。

非静态内部类或访问其封闭类的私有成员的内部类将在其中包含少量额外代码。对于非静态内部类,编译器添加一个引用封闭实例的成员变量。如果内部类访问封闭类的任何私有成员,编译器将在封闭类中合成具有“包私有”(默认)可访问性的访问器。

于 2009-10-01T15:08:53.777 回答