【问题标题】:Java generic interfacesJava 泛型接口
【发布时间】:2012-10-26 12:45:45
【问题描述】:

我有泛型类类型,T如下:

class MyClass<T>

我也知道T是接口,里面只有一个方法但是不知道是什么接口,我写不出来:

class MyClass< T extends TheInterface >

那么有没有办法调用这个方法呢?

public void callMe(T me, Object...params){
    // How can I invoke T interface method?
}

我一直在尝试这个:

public void callMe(T me, Object... params) {
// methods.length is 244, just as in my activity class
        Method[] methods = me.getClass().getMethods(); 
        try {
            methods[0].invoke(me, params);
        } catch (IllegalArgumentException e) {
            e.printStackTrace();
            return;
        } catch (IllegalAccessException e) {
            e.printStackTrace();
            return;
        } catch (InvocationTargetException e) {
            e.printStackTrace();
            return;


        }
}

但它不起作用

编辑:我发布了新的question,解释了我为什么需要这个

【问题讨论】:

  • 什么不起作用?请错误提示
  • 无法提前知道你会得到什么接口(或超级接口)听起来很像设计中的问题。依靠反射来调用方法很少是一个好的策略。我个人的经验建议你应该找到一种方法来改进设计(也许使用Adapter pattern),而不是尝试在运行时调用一个你甚至不知道名称的方法。

标签: java class interface


【解决方案1】:

是的,你必须写:

class MyClass< T extends TheInterface >

有了这些信息,编译器就知道 T 有一个名为 callMe 的操作

【讨论】:

  • 好的。您能否重新考虑设计以使这种方法成为可能?
  • 不,我不能,每次都是不同的界面,没有共同点
  • @Babibu 每次它都会是一个没有共同点的不同接口,但每个接口都有一个总是需要调用的方法?
  • 是的,这正是我需要的。
  • @Babibu:请提供更多关于您计划实现的目标的信息,以便我们更好地了解如何实现它。接口来自哪里?
【解决方案2】:

我不确定,你在寻找Strategy 模式吗?

【讨论】:

  • 不,这不是我要找的
【解决方案3】:

如果您不能更改 MyClass 中的声明,那么您可以只进行类型转换。

    public void callMe(T me, Object... params) {
        Someinterface instance = (Someinterface) me;
        list.callMe(me, params);
    }

但仍然像下面这样声明应该是最好的解决方案

class MyClass<T extends Someinterface >

下面是使用reflection的简单演示

 class MyClass<T> {
    public void callMe(T me, Object... params) throws SecurityException,
            NoSuchMethodException {
        // How can I invoke T interface method?
        Method size = me.getClass().getMethod("size", null);
        Method add = me.getClass().getMethod("add", Object.class);

        try {
            add.invoke(me, 10);
            System.out.println(size.invoke(me, params));

        } catch (IllegalArgumentException e) {
            e.printStackTrace();
            return;
        } catch (IllegalAccessException e) {
            e.printStackTrace();
            return;
        } catch (InvocationTargetException e) {
            e.printStackTrace();
            return;

        }
    }
}


    MyClass<List> myclass = new MyClass<List>();
    myclass.callMe(new ArrayList(), null);

输出:

  1 

【讨论】:

  • 我不明白你所说的类型转换是什么意思。我也不知道那个方法的名字,所以我不能像在你的例子中那样用“size”和“add”调用它
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2014-05-03
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-07-05
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多