繁体   English   中英

如何在Java中组合两个对象?

[英]How do I combine two objects in Java?

考虑:

public class test01{

    public void doSomething(){
        // do something
    }

}

public class test02{

    public void printSomething(){
        // print something
    }

} 

// in main
test01 t1 = new test01();
test02 t2 = new test02();

// I want do to something like this
test01 t3 = t1.merge(t2);

// with t3 I should be able to access both t1 and t2 functions
t3.doSomething();
t3.printSomething();

如果可以在Java中使用,请告诉我? 如果是,那么让我知道如何实现这一目标?

java中没有多重继承。 你可以做的是使test02的子类test01然后创建test03作为的子类test02

要么

你可以把它们组成一个像这样的Test03类:

public class Test03 {

    private Test01 test01;
    private Test02 test02;

    public void doSomething() {
        test01.doSomething();
    }

    public void printSomething() {
        test02.printSomething();
    }

}

请注意 ,在java中,您不应该使用像test01这样的类名。 它们应该是有意义的并且符合java类命名准则。

你最好的选择可能就是:

public class TestSet {
    private test01 t1 = new test01();
    private test02 t2 = new test02();

    public void doSomething() {
        t1.doSomething();
    }

    public void printSomething() {
        t2.printSomething();
    }
}

在某些语言中,支持多重继承,这可能是您在这里寻找的。 但不是用Java。 您可能想要也可能不想在这里创建几个接口,以便将TestSet与test01和test02更紧密地结合在一起。

如果可以在Java中使用,请告诉我?

这不可能。 您无法像Java中那样动态组合行为。

在Java中组合行为的常规方法是使用继承和包装或委派的某种组合。 即使这样,也会出现子类型的问题......除非你使用接口......因为Java不允许类有多个(直接)超类。

考虑@ Panzercrisis的例子。 虽然他的test03类实现具有相同签名的方法test01test02类的一个实例test03不是类型与其中任何兼容。 (您不能将test03实例用作test01test02不支持duck typing!)

为了解决这个问题,您需要分别定义由test01test02实现的接口face01face02 然后,你将实现test03为实现 face01face02

但这是所有静态类和静态类型。


在某些情况下,您可以使用DynamicProxy或类似的东西来“合成”一个“合并”两个现有类的行为的类。 但是,这些都是在幕后使用静态类型和代码生成完成的。 而且,这种方法只有在你有远见来定义一堆接口(例如face01face02 )并根据接口而不是实现类编写应用程序代码时才可行。

你可以在另一个类X中将类Y定义为内部类,并且可以在类X中使用类Y.除此之外,我知道没有办法做到这一点。

简短的回答,不,你不可能如何描述。

如果test01test02接口和你有第三类test03实现这两者,那么这样做的外观可能是可能的。 在C ++中,这可以通过多重继承来完成,但是它的功能大致相同(即你必须创建第三个类,而不是扩展它们),而且无论如何这个选项在Java中都不可用。

另一种选择是@Panzercrisis描述的某种组合。

最后的选择(我能想到的)是test02扩展test01但是改变了test02

但一般来说,不,不可能。

不,你不能,真正按照你描述的方式做到这一点,你可以做到

公共类test01扩展test02 {....

}

所以你的test1,你可以使用这两个类中的方法,但是如果你真的想要将这些类合并在一起,你可以像这样做一些令人厌恶的事:

public class MyObject {
    Map<String, Object> objects = new HashMap<String, Object>();
    Map<String, Method> methods = new HashMap<String, Method>();

    public Object execute(String methodAName)
{

    Object object = objects.get(methodAName);
    Method method = methods.get(methodAName);
    if (object==null || method==null)
    {
        throw new RuntimeException("method not found");
    }

    try {
        return method.invoke(object, null);
    } catch (Exception e) {
        throw new RuntimeException(e);

    }
}

    public void merge(Object o) {
        for (Method m : o.getClass().getMethods()) {
            objects.put(m.getName(), o);
            methods.put(m.getName(), m);
        }
    }
}

当你可以这样使用它

 MyObject o = new MyObject();
 o.merge(new test01());
 o.merge(new test02());

 o.execute("printSomething");
 o.execute("doSomething");

但正如我所说,不推荐

你可以使用Java inheritance做类似的事情,但不是一回事。 你可以在这里使用extends 但是你必须确保方法覆盖不会发生,否则你的要求不匹配。

Test02 extends Test01

然后

Test03 extends Test02 

现在你可以实现类似的东西了。

Test03 test=new Test03();

test.callMethodInTest1();
test.callMethodInTest2(); 

样品:

public class Test1 {

public String callMethodInTest1() {
    return "test1";
  }
}

public class Test2 extends Test1{

public String callMethodInTest2() {
    return "test2";
  }
}

public class Test03 extends Test2 {

public static void main(String[] args){
   Test03 sample=new Test03();
   sample.callMethodInTest1();
   sample.callMethodInTest2();
 }

}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM