cn.hutool.core.builder.GenericBuilder Maven / Gradle / Ivy
package cn.hutool.core.builder;
import cn.hutool.core.lang.func.Consumer3;
import cn.hutool.core.lang.func.Supplier1;
import cn.hutool.core.lang.func.Supplier2;
import cn.hutool.core.lang.func.Supplier3;
import cn.hutool.core.lang.func.Supplier4;
import cn.hutool.core.lang.func.Supplier5;
import java.util.ArrayList;
import java.util.List;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import java.util.function.Supplier;
/**
* 通用Builder
* 参考: 一看就会的java8通用Builder
* 使用方法如下:
*
* Box box = GenericBuilder
* .of(Box::new)
* .with(Box::setId, 1024L)
* .with(Box::setTitle, "Hello World!")
* .with(Box::setLength, 9)
* .with(Box::setWidth, 8)
* .with(Box::setHeight, 7)
* .build();
*
*
*
* 我们也可以对已创建的对象进行修改:
*
* Box boxModified = GenericBuilder
* .of(() -> box)
* .with(Box::setTitle, "Hello Friend!")
* .with(Box::setLength, 3)
* .with(Box::setWidth, 4)
* .with(Box::setHeight, 5)
* .build();
*
* 我们还可以对这样调用有参构造,这对于创建一些在有参构造中包含初始化函数的对象是有意义的:
*
* Box box1 = GenericBuilder
* .of(Box::new, 2048L, "Hello Partner!", 222, 333, 444)
* .with(Box::alis)
* .build();
*
* 还可能这样构建Map对象:
* {@code
* HashMap colorMap = GenericBuilder
* .of(HashMap::new)
* .with(Map::put, "red", "#FF0000")
* .with(Map::put, "yellow", "#FFFF00")
* .with(Map::put, "blue", "#0000FF")
* .build();
* }
*
* 注意:本工具类支持调用的构造方法的参数数量不超过5个,一般方法的参数数量不超过2个,更多的参数不利于阅读和维护。
*
* @author TomXin
* @since 5.7.21
*/
public class GenericBuilder implements Builder {
private static final long serialVersionUID = 1L;
/**
* 实例化器
*/
private final Supplier instant;
/**
* 修改器列表
*/
private final List> modifiers = new ArrayList<>();
/**
* 构造
*
* @param instant 实例化器
*/
public GenericBuilder(Supplier instant) {
this.instant = instant;
}
/**
* 通过无参数实例化器创建GenericBuilder
*
* @param instant 实例化器
* @param 目标类型
* @return GenericBuilder对象
*/
public static GenericBuilder of(Supplier instant) {
return new GenericBuilder<>(instant);
}
/**
* 通过1参数实例化器创建GenericBuilder
*
* @param instant 实例化器
* @param p1 参数一
* @param 目标类型
* @param 参数一类型
* @return GenericBuilder对象
*/
public static GenericBuilder of(Supplier1 instant, P1 p1) {
return of(instant.toSupplier(p1));
}
/**
* 通过2参数实例化器创建GenericBuilder
*
* @param instant 实例化器
* @param p1 参数一
* @param p2 参数二
* @param 目标类型
* @param 参数一类型
* @param 参数二类型
* @return GenericBuilder对象
*/
public static GenericBuilder of(Supplier2 instant, P1 p1, P2 p2) {
return of(instant.toSupplier(p1, p2));
}
/**
* 通过3参数实例化器创建GenericBuilder
*
* @param instant 实例化器
* @param p1 参数一
* @param p2 参数二
* @param p3 参数三
* @param 目标类型
* @param 参数一类型
* @param 参数二类型
* @param 参数三类型
* @return GenericBuilder对象
*/
public static GenericBuilder of(Supplier3 instant, P1 p1, P2 p2, P3 p3) {
return of(instant.toSupplier(p1, p2, p3));
}
/**
* 通过4参数实例化器创建GenericBuilder
*
* @param instant 实例化器
* @param p1 参数一
* @param p2 参数二
* @param p3 参数三
* @param p4 参数四
* @param 目标类型
* @param 参数一类型
* @param 参数二类型
* @param 参数三类型
* @param 参数四类型
* @return GenericBuilder对象
*/
public static GenericBuilder of(Supplier4 instant, P1 p1, P2 p2, P3 p3, P4 p4) {
return of(instant.toSupplier(p1, p2, p3, p4));
}
/**
* 通过5参数实例化器创建GenericBuilder
*
* @param instant 实例化器
* @param p1 参数一
* @param p2 参数二
* @param p3 参数三
* @param p4 参数四
* @param p5 参数五
* @param 目标类型
* @param 参数一类型
* @param 参数二类型
* @param 参数三类型
* @param 参数四类型
* @param 参数五类型
* @return GenericBuilder对象
*/
public static GenericBuilder of(Supplier5 instant, P1 p1, P2 p2, P3 p3, P4 p4, P5 p5) {
return of(instant.toSupplier(p1, p2, p3, p4, p5));
}
/**
* 调用无参数方法
*
* @param consumer 无参数Consumer
* @return GenericBuilder对象
*/
public GenericBuilder with(Consumer consumer) {
modifiers.add(consumer);
return this;
}
/**
* 调用1参数方法
*
* @param consumer 1参数Consumer
* @param p1 参数一
* @param 参数一类型
* @return GenericBuilder对象
*/
public GenericBuilder with(BiConsumer consumer, P1 p1) {
modifiers.add(instant -> consumer.accept(instant, p1));
return this;
}
/**
* 调用2参数方法
*
* @param consumer 2参数Consumer
* @param p1 参数一
* @param p2 参数二
* @param 参数一类型
* @param 参数二类型
* @return GenericBuilder对象
*/
public GenericBuilder with(Consumer3 consumer, P1 p1, P2 p2) {
modifiers.add(instant -> consumer.accept(instant, p1, p2));
return this;
}
/**
* 构建
*
* @return 目标对象
*/
@Override
public T build() {
T value = instant.get();
modifiers.forEach(modifier -> modifier.accept(value));
modifiers.clear();
return value;
}
}