Java为复合行为

时间:2015-06-06 13:20:53

标签: java generics reflection annotations composite

我是java的初学者,所以需要你的专业建议。

简短说明:

  • 我有一些课程A1,A2,A3 .. B1 ..
  • 我需要一个创建CompositeA CompositeB的魔术泛型类或方法......
  • 这些复合类已定义了广义行为,如何处理何种方法
  • 可以通过注释设置方法类型
  • 方法本身对于A,B ..
  • 是不同的
  • 我希望每次有新的X类时都避免编写CompositeX类。
  • 问题:有可能吗?如果是,怎么样?

详细说明:

我们现在的问题:
2 + 数据源,如DB,文件,库 从这些数据源我们得到类似的信息。例如ID。
信息在对象(如hibernate实体)中,它扩展了一个接口/抽象类 例如,如果我们需要的内容是Foo类,那么我们有FooDB,FooFile,FooLib。所有实施/扩展Foo。
我们创建了一些CombinedFoo,以处理所有这些来源的组合数据。

要更新 CombinedFoo数据源(插入或更改某些信息),只会使用一个来源用于retreiving 来自CombinedFoo的数据所有来源将被使用 (稍后参见CompositeFoo构造函数)

例如,我有一个Foo对象,它有来自DB的数据(在本例中为ID),另一个来自文件的Foo和来自某些lib的另一个Foo。 所有这些Foo都实现了相同的Foo接口 现在我需要一个组合对象中的所有源代码(也实现了Foo接口) 通过组合foo的初始化我做

CompositeFoo compFoo = new CompositeFoo(fooDB, fooFILE, fooLIB)  

compFoo.addId("value")仅拨打fooDB.addId("value") compFoo.getIds()获取所有数据源的所有ID (fooDB.getIds() + fooFILE.getIds() + fooLIB.getIds())。

如果我不仅需要Foo,而且例如Bar,我需要使用自己的方法再次实现新的CompositeBar(我想避免这种情况)。但最终我需要的是:确保哪些方法仅用于检索(get_methods)以及用于更改信息的方法(set_methods)。

现在的问题是: 是否有可能创建这样的魔术泛型类,即写入一次,并且可以应用于每个对象类,我想要组合吗?

这里有一些更深入理解的例子:

import java.util.Collections;
import java.util.HashSet;
import java.util.Set;

//interface used for composite class and data classes
public abstract class Foo {
    abstract Set<String> getIds();
    abstract void addId(String id);
}

//data source from file
class FooFromFile extends Foo {

    @Override
    Set<String> getIds() {
        //loads data from file
    }

    @Override
    void addId(String id) {
        //changes file, add there one id
    }
}

//data source from DB
class FooFromDB extends Foo {

    @Override
    Set<String> getIds() {
        //loads ids from DataBase
    }

    @Override
    void addId(String id) {
        //adds id to database
    }
}

//class i use now, combines all Foo's
//gets info from all, updates only main data source
//this one i want to make generic
class CompositeFoo extends Foo {
    private Foo mainFoo;
    private Set<Foo> others;

    public CompositeFoo(Foo mainSource, Foo ...otherSources ) {
        mainFoo = mainSource;
        others = new HashSet<>();
        Collections.addAll(others, otherSources);
    }

    @Override
    Set<String> getIds() {
        HashSet<String> result = new HashSet<>();
        //load from main source
        result.addAll(mainFoo.getIds());
        //and from other sources
        for (Foo otherFoo : others ) {
            result.addAll(otherFoo.getIds());
        }
        //ids from all the sources
        return result;
    }

    @Override
    void addId(String id) {
        //uses only main source, we don't want to add ID to all the sources
        mainFoo.addId(id);
    }
}

现在它的工作原理如下:

public static void main(String[] args) {
        FooFromDB dbFooMain = new FooFromDB();
        FooFromFile fileFoo = new FooFromFile();
        CompositeFoo compFoo= new CompositeFoo(dbFooMain, fileFoo);

        compFoo.add("new id"); //adds to dbFooMain only
        compFoo.getIds(); //gets from all sources (dbFooMain  + fileFoo)
    }

这种魔法我想要实现,但不知道如何:

它应该以某种方式在这个例子中起作用

    public static void main(String[] args) {
        FooFromDB dbFooMain = new FooFromDB();
        FooFromFile fileFoo = new FooFromFile();

        //something like this:
        MagicComposite<Foo> compFoo = new MagicComposite<>(dbFooMain, fileFoo);
        //or something like this:
        Foo compFoo = AnyCompositeFactory.createComposite(Foo.class, dbFoo, fileFoo);

        //than this should work
        //adds to dbFooMain only. dbFoo.add("new id") called
        compFoo.add("new id"); 

        //gets ids from all sources so dbFoo.getIds() + fileFoo.getIds() called and combined
        compFoo.getIds();


        //-----------------------------------------
        //for Bar the same magic class should do
        MagicComposite<Bar> compBar = new MagicComposite<>(dbBarMain, fileBar);
        //or
        Bar compBar = AnyCompositeFactory.createComposite(Bar.class, dbBar, fileBar);
    }

所以我想避免为每个Composite%ClassName%数据类创建%ClassName%。 我需要一些动态的,通用的CompositeMagic<Class>或其他什么。

我的想象...... 如果我有Bar类,我会以某种方式对其进行注释,将哪些方法组合起来获取所有信息,以及哪些方法仅用于更改信息。

abstract class Bar{

    @Magic(Type = retrieveInformationOnly)
    Set<String> getSomething();

    @Magic(Type = addInformation)
    void addSomething(String id);
}

在这种情况下if if我用其他一些Bars初始化CombinedBar,并调用这个复合对象的addSomething(),而不是只有main(构造函数中的第一个arg)数据源应该添加信息,如果我调用{{1调用所有初始化的类,并返回组合结果。 (参见CompositeFoo实现)

实施可能是另一回事。这里的代码示例只是为了澄清我需要的东西。

0 个答案:

没有答案