0

Here's a simple example:

class World<S extends Sprites, B extends Bodies> {

// Both  of these have a problem...

static World world = null; // "World is a raw type. References to generic type
                           // World<BOD,SPRT> should be parameterized"

static World<S, B> world = null; // "Cannot make a static reference to the non-static type S
                       // "Cannot make a static reference to the non-static type B

// The following is allowed but looks ugly/fishy to me
static World<?, ?> world = null; //

In case you are wondering, I am trying to get a singleton pattern going. The challenge is that this class is extended in a separate package GAME , and I cannot have this package (MODEL) have any dependency on that GAME. Therefore the constructor has to be MODEL. So it would be OK to have the Constructor store the singleton object in the static variable of this class in MODEL.

Is the static World<?, ?> world = null; indeed ugly in your opinion and is there a better way to approach this?

halfer
  • 19,824
  • 17
  • 99
  • 186
pitosalas
  • 10,286
  • 12
  • 72
  • 120
  • 3
    Remember that Java has type-erasure; there will be only one static `world` variable, no matter how many different ways you instantiate the `World` class (because they all share the same class as far as the runtime is concerned). – Oliver Charlesworth Feb 17 '12 at 20:02
  • I wouldn't make World a singleton/static in the first place. What happens when you write a different GAME where two worlds exist? In any case, it seems to me that it is up to whatever is in your `GAME` package to make sure _it_ only creates one `World`. This in now way answers your question, it avoids the question instead. – Stephen P Feb 17 '12 at 20:33
  • Good points... In fact my GAME package implements a conventional singleton to ensure there is only one... – pitosalas Feb 18 '12 at 22:44

2 Answers2

4

You cannot access generic type parameters in static methods or fields, as stated in this answer. Because static fields are shared across all instances of the class (in this case I guess your class would be Model), how would this simultaneously work for Model<Sprites, Bodies> and Model<ClassA, ClassB>?

Community
  • 1
  • 1
Andres F.
  • 403
  • 1
  • 13
  • 24
  • Yeah that makes perfect sense... It explains why static World failed to compile. However how does World, ?> get away with it? – pitosalas Feb 18 '12 at 22:45
  • @pitosalas Because `?` is a wildcard which means "any type". Therefore `World, ?>` in this case is like writing plain `World`, and is not constrained by the type parameters of `Model` (remember this was the source of your compilation error). – Andres F. Feb 18 '12 at 22:53
  • Do people think that writing World, ?> in a situation like this is ugly or is it perfectly clean? Is it uglier than writing plain World which also is accepted with a warning? – pitosalas Feb 18 '12 at 23:05
  • @pitosalas `World, ?>` is probably not what you want either. Note you cannot add anything to a container parameterized with a wildcard (try adding something to a `List>` and see what happens). The takeaway lesson here is that **your design is dodgy**; try redesigning your code so that you don't need to use `>` or statics. You probably don't even need a singleton anyway. – Andres F. Feb 19 '12 at 00:11
2

Surely if you want a singleton, you have to know up front what the exact types referred to in that single instance will be.

Maybe if you add more detail to your example, this will no longer be true but as far as I can see, you don't need generics here. If you want to express that the fields you store Sprites and Bodies can be any subclass of these classes, just declare those fields with these types, inheritance will take care of the rest.

Just think of the name: "generics", it is to be used for something that will be reused in different contexts over and over again. Like a class defining a tree structure, which can then hold any class of objects. Sometimes it's hard to tell whether you need generics or not. But a singleton is definitely the polar opposite; there's nothing less generic than a singleton: one class, a single instance.

P.s.: There are however Enums, which are both generic and have a fixed number of instances, self-bound generic types are the solution for these cases, but I'm almost certain you don't need this.

biziclop
  • 48,926
  • 12
  • 77
  • 104
  • Yes I do know up front... But, there are other reasons that lead me to use generics having to do with keeping the package separation leak-proof while avoiding a lot of annoying casting. In fact the model for this came from another StackOverflow thread: http://stackoverflow.com/questions/9270466/java-generics-having-trouble-with-a-tricky-situation/9280277#9280277 – pitosalas Feb 18 '12 at 22:48
  • @pitosalas Maybe a bigger code sample and a little explanation could help us identify the solution you need then. As it stands, the answer to your question really is that you can't parametrise a static field. – biziclop Feb 19 '12 at 13:34
  • I hesitate to burden this list with a longer code sample... I don't want to be slapped :) – pitosalas Feb 20 '12 at 14:28