1

I am trying to create a collecion of objects using reflection. I have the class name. But at compile time have no idea about the constructor. I used this tutorial.

import java.lang.reflect.*;

  public class constructor2 {
      public constructor2()
      {
      }

  public constructor2(int a, int b)
  {
     System.out.println(
       "a = " + a + " b = " + b);
  }

  public static void main(String args[])
  {
     try {
       Class cls = Class.forName("constructor2");
       Class partypes[] = new Class[2];
        partypes[0] = Integer.TYPE;
        partypes[1] = Integer.TYPE;
        Constructor ct 
          = cls.getConstructor(partypes);
        Object arglist[] = new Object[2];
        arglist[0] = new Integer(37);
        arglist[1] = new Integer(47);
        Object retobj = ct.newInstance(arglist);
     }
     catch (Throwable e) {
        System.err.println(e);
     }
  }

}

Now let's say I don't know abut the parameters of the constructors. (Whether it's a default constructor or two integers). The costructor parameters can change from class to class. I have no idea about the Constructor2 class. But I have the className. So I cant create the "argList" as above. Any idea how I can create a object from constructors then.

I did as follows

Constructor[] brickConstructorsArray = brickClass.getConstructors();
            for (Constructor constructor : brickConstructorsArray) {
                Class[] constructorParams = constructor.getParameterTypes();

                Object argList[] = new Object[constructorParams.length];
                int index = 0;
                for (Class cls : constructorParams) {

                    if (cls.equals(Sprite.class)) {
                        Object spriteOb = foundSprite;
                        argList[index] = spriteOb;
                    } else if (cls.equals(double.class)) {
                        Object dblObj = new Double(0.0);
                        argList[index] = dblObj;
                    }

                    index++;
                }
                brickObject = (Brick) constructor.newInstance(argList);

            }

This would work for costrcutors which will have Sprite or double parameters. To include other possibilities I'd have to create a loooong if else chain. Need help.

2
  • 2
    But why would you need to do that in the first place? Commented Jul 1, 2012 at 7:10
  • This is why you avoid reflection and find a better solution. Commented Jul 1, 2012 at 9:55

1 Answer 1

3

Do you really not care what values you're going to pass? You could have a map from each primitive class to a default value of its wrapper type:

// You can make this a static member somewhere
Map<Class<?>, Object> primitiveValues = new HashMap<Class<?>, Object>();
primitiveValues.put(char.class, '\0');
// etc

... and just use null for any non-primitive type. So:

Constructor[] brickConstructorsArray = brickClass.getConstructors();
for (Constructor constructor : brickConstructorsArray) {
    Class[] constructorParams = constructor.getParameterTypes();

    Object argList[] = new Object[constructorParams.length];

    // When you need the index, there's no point in using the enhanced
    // for loop.
    for (int i = 0; i < constructorParams.length; i++) {
        // Fetching the value for any non-primitive type will 
        // give null, which is what we were going to use anyway.
        argList[i] = primitiveValues.get(constructorParams[i]);
    }

    brickObject = (Brick) constructor.newInstance(argList);
}

Of course I'd expect this to fail quite often. After all, if you don't know anything about the constructor you're calling, you have no idea what arguments are going to be valid.

Is this really something you're expecting to find useful?

Sign up to request clarification or add additional context in comments.

1 Comment

This was required to instantiate objects of any class in a series of related classes. This constructor method was futile. So I used another method from ObjectOutPutStream class that created an object of any class instead.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.