views:

216

answers:

4

How would I be able to accomplish the following:

public class testClass implements Interface {
     public testClass(Interface[] args) {
     }
}

So that I could declare

Interface testObject = new testClass(new class1(4), new class2(5));

Where class1 and class2 are also classes that implement Interface.

Also, once I accomplish this, how would I be able to refer to each individual parameter taken in to be used in testClass?

Thanks :)

+4  A: 

You can use varargs, which are treated as arrays. For example:

public testClass(Interface... args) {
    System.out.println(args[0]);
}
someguy
can throw `ArrayIndexOutOfBoundsException`
Roman
@Roman: How? The example only accesses the very first element.
someguy
That's why you check `args.length` first.
Donal Fellows
@someguy: if none Interface instance is passed as a parameter then args would be an empty array.
Roman
Guys, it's only an example showing how he can access an argument taken from a vararg.
someguy
+8  A: 

So that I could declare

Interface testObject = new testClass(new class1(4), new class2(5));

You need to use varargs in testClass constructor:

public testClass (Interface ... args) {
   for (Interface i : args) {
      doSmthWithInterface (i);
   }
}
Roman
An added note for those who don't already know: you will have to use Java 1.5 or later to use varargs and that particular loop syntax.
JavadocMD
A: 

Like this (save the whole sample into a file, say testClass.java):

interface Interface{}

public class testClass implements Interface 
{
     public testClass(Interface ... args) 
     {
        System.out.println("\nargs count = " + args.length);
        for( Interface i : args )
        {
            System.out.println( i.toString() );
        }
     }

     public static void main(String[] args)
     {
         new testClass(
          new Interface(){}, // has no toString() method, so it will print gibberish
          new Interface(){ public String toString(){return "I'm alive!"; } }, 
          new Interface(){ public String toString(){return "me, too"; } }
         );

         new testClass(); // the compiler will create a zero-length array as argument
     }
}

The output will be as follows:

C:\temp>javac testClass.java

C:\temp>java testClass

args count = 3
testClass$1@1f6a7b9
I'm alive!
me, too

args count = 0
luis.espinal
A: 

You don't have to use varargs, you can use an array as an input parameter, varargs is basically just a fancy new syntax for an array parameter, but it will help prevent you from having to construct your own array in the calling class.
i.e. varargs allow (parm1, parm2) to be received into an array structure

You cannot use an interface to enforce a Constructor, you should probably use a common abstract super class with the desired constructor.

public abstract class Supa {

    private Supa[] components = null;

    public Supa(Supa... args) {
        components = args;
    }

}
public class TestClass extends Supa {

    public TestClass(Supa... args) {
        super(args);
    }

    public static void main(String[] args) {
        Supa supa = new TestClass(new Class1(4), new Class2(5));
            // Class1 & Class2 similarly extend Supa
    }
}

Also see the composite design pattern http://en.wikipedia.org/wiki/Composite_pattern

crowne
You can't pass an interface explicitly obviously. However, nothing's stopping you from passing classes that inherit that interface (which is what the OP's example did).
someguy
You can pass the interface explicitly if you cast the class to an interface variable then pass the interface variable.But the biggest problem that I see is that you cannot use an interface to enforce implementers to provide a predetermined constructor, for that you have to use an abstract super class.
crowne