Petter Thowsen
Petter Thowsen

Reputation: 1727

Java Registry Class?

I'm fairly new to Java. I'm coming from PHP and I used to create registry classes in php using the magic __get and __set methods. So that other parts of the system can easily do:

registry.foo = new Foo();

I should mention I'm trying to create game engine. Here is my registry in Java atm:

class Registry {

    private static Map<String, Object> box = new HashMap<String, Object>();

    public static Object get(String key) {

        if (Registry.box.get(key) != null) {
            return Registry.box.get(key);
        }else {
            return null;
        }
    }

    public static void set(String key, Object o) {
        Registry.box.put(key, o);
    }

}

Then for the other parts of the system to access the registry, I currently need this whole thing:

((Object) Registry.get("Object")).doSomething();

Which is really a lot of code. In php this would be accomplished by simply:

Registry.foo.doSomething();

Any way to make this a bit more simpler? I guess I could make public fields, but then the regsitry class would need to implicitly create these fields as the possibility of new objects may need to be added which are unknown to the registry class itself, which is.. annoying :P

Thanks in advance!

Upvotes: 4

Views: 3064

Answers (3)

millimoose
millimoose

Reputation: 39950

Any way to make this a bit more simpler?

Not in any practical way. Java is a statically typed language, and the structure of objects has to be known up front. The very idea of an equivalent of PHP's __get and __set is antithetical to the language.

For what it's worth, your "registry" looks like bad design anyway. (Admittedly making some pretty wild assumptions from the little code you've shown.) You shouldn't need a global repository of what appear to be unrelated objects. You should consider some sort of dependency injection instead.

Based on your comment, instead of structuring your code like this:

class World implements GameSystem {

    public void update() {
        Registry.get("game").doSomething();
    }

}

you should do:

class World implements GameSystem {

    Game game;
    public World(Game game) { // and other dependencies
        this.game = game;
    }

    public void update() {
        this.game.doSomething();
    }

}

The idea is that components of your program don't really have any business knowing how to find the other components. It also makes dependencies between the components explicit, and helps you avoid circular dependencies.

Upvotes: 1

Eugene Retunsky
Eugene Retunsky

Reputation: 13139

First of all this method is too verbose:

public static Object get(String key) {
    if (Registry.box.get(key) != null) {
        return Registry.box.get(key);
    }else {
        return null;
    }
}

It could be just:

public static Object get(String key) {
   return Registry.box.get(key);
}

But second, this is definitely a bad design. Global repository - doesn't sound reasonable. A storage of objects of all types by string key - it's terrible.

Upvotes: 2

Yann Ramin
Yann Ramin

Reputation: 33177

This is a two pronged problem:

  1. Java is a statically type language, and does not offer in-language flexibility for defining objects at runtime (you can use a library to synthesize classes at runtime, but, see #2)
  2. A global registry for objects defeats a lot of safeties in a type-safe language. If your entire application centers around getting and putting objects into a global Map, there likely safer and less-coupled designs.

How can this be solved?

  1. Redesign your application structure to not need a global map.
  2. Use a dynamic language subset for Java (such as Groovy).
  3. Use Scala 2.10 (JVM compatible) which features a Dynamic type which does exactly what you want.

Upvotes: 4

Related Questions