编程语言
首页 > 编程语言> > 具有getter和setter的对象的Fluent Interface(Java)

具有getter和setter的对象的Fluent Interface(Java)

作者:互联网

我阅读并欣赏了Lukas Eder的文章http://blog.jooq.org/2012/01/05/the-java-fluent-api-designer-crash-course/,我想为一堂课创建一个Fluent界面.

该类有四个函数(“words”fill1到fill4),它们允许设置对象属性和四个函数(“words”get1 to get4)获取这些属性,但只有在设置了所需的属性时:

首先,我必须填写基本设置(fill1).之后我或者能够获得一些这些设置(get1到get3),这些是Strings.或者我可以填写更多信息(fill2到fill4).但是只有在每次fill2到fill4被调用至少一次之后,才能调用最终的get4.我该怎么做呢?

第一个图(状态是黑点)显示我想要做什么,但你可以看到?标记不清楚的部分,因为如果保留在第一个图形中,即使只调用了fill2到fill4中的一个,它也会允许调用get4.

第二个图表会强制调用每个fill2到fill4,但强制执行订单并限制如果我想更改,例如fill3,我还要重置fill2和fill4.

最后一个图表会做我想要的,但它有13个状态!现在,如果我想象我只会在fill2到fill4的组中再添加一个属性,那么状态的数量会更多.

enter image description here

编辑:此外,在考虑了一些之后,我注意到我这样做的方式(见下文)甚至无法实现最后一个图,因为在调用fill2之后,我们可能处于不同的状态 – 取决于之前发生的事情.

我能做什么/应该做什么?

编辑:我实现我的流畅的界面有点像一个立面(如果我有正确的设计模式).我的意思是:我让实际的类几乎不受影响 – 返回它(如方法链接),但是在方法签名中将相应的状态接口作为返回值.状态由嵌套接口表示.例:

public class MyClass implements MyInterface.Empty, MyInterface.Full {

    String stuff;

    private MyClass(){};

    public static MyInterface.Empty manufactureNewInstance(){
        return new MyClass();
    }

    public MyInterface.Full fillStuff(String stuff){
        this.stuff = stuff;
        return this;
    }

    public String getStuff(){
        return stuff;
    }

}

public interface MyInterface {

    public interface Empty {
        public MyInterface.Full fillStuff();
    }

    public interface Full {
        public String getStuff();
    }

}

public class MyMain {

    pulic static void main(String[] args) {

        // For explaination:
        MyClass.Empty myclassEmpty = MyClass.manufactureNewInstance();
        MyClass.Full myclassFull = myclassEmpty.fillStuff("Hello World 1!");
        String result1 = myclassEmpty.getStuff();

        // As fluent chaining:
        String result2 = MyClass.manufactureNewInstance()
            .fillStuff("Hello World 2!")
            .getStuff();

    }

}

解决方法:

Java中的Fluent接口API在某种程度上受限于您需要通过不同类型表示每个API状态的事实.这是Java类型是将一组API约束传递给Java编译器以进行验证的唯一方法的结果.

显然,在创建流畅的API时,这是一个不幸的限制.要克服此限制,您需要:

>通过例如接口手动实现所有API状态.如果您的代码不太可能发生变化,这可能是一个可行的解决方案.在一个范围相当有限的项目中,不应该活得太久.然后,单个支持类可以实现代表每个API状态的所有接口.只要用户不使用反射或类型转换,编译器就会验证是否以合法的顺序调用方法.
>自动生成代码.这是一种更加雄心勃勃的方法,但如果您的API状态组合“爆炸”,它可以为您节省大量的打字和重构工作.我写了一个名为Byte Buddy的代码生成库,我知道用户使用该库为流畅的API创建接口. (不幸的是,我在这个问题上与之联系的两个用户没有开源他们的代码.)如果您更愿意创建Java源代码而不是Java字节代码,那么Java poet可能是您的替代方案,我也有看到这个用例.
>简化您的API以仅验证最常见的错误,同时检查运行时异常中不常见的错误.这通常是一个可行的解决方案,因为它使API更加平易近人.

标签:java,fluent-interface
来源: https://codeday.me/bug/20190519/1136654.html