用整数id创建类实例的模式?

时间:2009-09-15 11:02:16

标签: java design-patterns

我正在读一个Stream,它提供了一个标识符(一个简单的int)。根据int的不同数据,我需要将其转化为对象。到目前为止,我为每个对象类型创建了类,每个类提供了一个read(InputStream输入)方法,该方法读取要为这种对象读取的任何数据(所有对象类都从公共基类继承)。 /> 但是,有许多id,因此有很多类。确定和创建类实例的最优雅方法是什么? 我首先尝试的最天真的方法是使用switch-case块来创建实例,但我发现它使代码混乱(不合理)。它还迫使我在编译时提供每个班级 第二个尝试是创建一个映射,将每个int映射到一个类,并使用newInstance()来创建对象。仍然存在我需要初始化地图的问题,这仍然要求我在编译时提供每个类。它或多或少只是将杂乱的地方从一个地方移到另一个地方 不需要删除编译时依赖项,如果可能的话,它只是一个奖励。主要目标是避免使用样板代码。

约束:我不想添加库来解决这个问题。我的反思很好。

3 个答案:

答案 0 :(得分:5)

另一种方法是仍然使用Map但基本上使用后期绑定,如果这是更可取的。您甚至可以将配置存储在属性文件中,如:

1=java.lang.String
2=my.class.Something
...etc...

然后你做这样的事情:

Map<Integer,ObjectFactory> loader = ... // load from properties; fairly trivial

假设:

public class ObjectFactory {
  private Final String className;
  private transient Class clazz;

  public ObjectFactory(String className) {
    this.className = className;
  }

  public Object createInstance() {
    try {
      if (clazz == null) {
        clazz = Class.forName(className);
      }
      return clazz.newInstance();
    } catch (Exception e) {
      throw new IllegalStateExxception("Could not crate " + className, e);
    }
  }
}

答案 1 :(得分:1)

我认为你的地图解决方案听起来不错,但是将初始地图设置移出Java代码并转移到配置文件中。 (Class.forName将在这里提供帮助)

答案 2 :(得分:1)

您可以拥有原型的注册表。

您希望能够创建的每个类的原型(在某个时间点)可以在运行时添加到您的注册表对象中,这些原型每个都有自己唯一的整数ID。

当你想要一个id为x的对象时,你只需要求你的注册表对象克隆并返回id为x的原型。 (如果当前没有注册此类原型,则返回null。)

在内部,注册表可以是用于快速检索的(哈希)映射,但它可以很容易地成为原型列表(确保所有原型实现注册表可以使用的公共接口)。最好的是,不需要反思!

相关问题