基础
链式编程定义:链式编程的原理就是返回一个 this 对象,就是返回本身,达到链式效果
public class User {
private Integer id;
private String name;
private Integer age;
public User setId(Integer id) {
this.id = id;
return this;
}
public User setName(String name) {
this.name = name;
return this;
}
public User setAge(Integer age) {
this.age = age;
return this;
}
}
StringBuilder 就使用了链式编程的写法:
// StringBuilder的append方法的源码
@Override
public StringBuilder append(String str) {
super.append(str);
return this;
}
// StringBuilder的append方法使用
StringBuilder builder = new StringBuilder();
builder.append("Hello").append("\t").append("world!");
lombok中使用链式编程
在 pom.xml 文件中引入 lombok 依赖:
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.18.14</version>
<scope>provided</scope>
</dependency>
lombok 实现链式编程:在 bean 上添加 @Accessors(chain = true)
@Data
@Accessors(chain = true)
public class User implements Serializable {
private static final long serialVersionUID = -1602774207630314992L;
private Integer id;
private String username;
private String password;
}
静态链式编程
静态的链式编程比普通的链式编程的好处:
- 创建对象更简单
- 可以在静态方法、静态代码块等中使用
- 对于必输字段,可以强制要求
屏蔽 class 的 new,只能通过静态方法创建新实例,如:
public class User {
private Integer id;
private String name;
private Integer age;
// 静态构造方法,避免外部调用
private User(){
}
// 对外提供的创建对象的方法
public static User of(){
return new User();
}
public User setId(Integer id) {
this.id = id;
return this;
}
public User setName(String name) {
this.name = name;
return this;
}
public User setAge(Integer age) {
this.age = age;
return this;
}
}
在创建 bean 时,存在一些必输字段,静态的链式编程可以声明这些必输字段:
public class User {
private Integer id;
private String name;
private Integer age;
// 静态构造方法,避免外部调用
private User(){
}
// 对外提供的创建对象的方法
public static User of(String name){
if (name == null) {
throw new NullPointerException("name is marked non-null but is null");
} else {
this.name = name;
}
}
public User setId(Integer id) {
this.id = id;
return this;
}
public User setName(String name) {
this.name = name;
return this;
}
public User setAge(Integer age) {
this.age = age;
return this;
}
}
lombok 使用静态链式编程
在 bean 上添加 @RequiredArgsConstructor(staticName = “of”) 注解就可以实现静态链式编程
- 其中 staticName 用来设置静态创建方法的名称
- 当需要设置某个参数必须在创建时提供的话,可以在相应的参数上添加 @NonNull 注解
@Data
@Accessors(chain = true) // 支持链式编程
@RequiredArgsConstructor(staticName = "of")
public class User implements Serializable {
private static final long serialVersionUID = -1602774207630314992L;
@NonNull
private Integer id;
private String username;
private String password;
}
builder 模式的链式 Bean
builder 模式实现原理为在 bean 里面创建一个 静态 builder 方法 和一个 静态内部Builder类,通过调用静态 builder 方法来创建 Builder 类,然后通过 builder 类中的 build 方法直接创建一个 Bean,具体实现:
public class User {
private Integer id;
private String name;
private String password;
public User(Integer id ,String name ,String password) {
this.id = id;
this.name = name;
this.password = password;
}
// 静态 builder 方法
public static User.Builder builder() {
return new User.Builder();
}
// 静态内部类 Builder
public static class Builder {
private Integer id;
private String name;
private String password;
public User.Builder id(Integer id) {
this.id = id;
return this;
}
public User.Builder name(String name) {
this.name = name;
return this;
}
public User.Builder password(String password) {
this.password = password;
return this;
}
public User build(){
return new User(id ,name ,password);
}
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
}
使用:
public static void main(String[] args) {
User user = User.builder().id(12).name("Bob").password("123456").build();
}
lombok 实现 builder 模式的链式 bean
lombok 实现 builder 模式的链式 bean,只需要在相应 bean 上添加一个注解:@Builder ,@Builder 注解中支持如下参数:
- builderClassName = “Builder”:内部创建类的名称
- builderMethodName = “builder”:获取静态内部类的方法
- buildMethodName = “build”:创建方法名称
- toBuilder = true:是否创建一个 toBuilder 方法,用于将外部类转换成一个构造器 Builder
有关 Builder 的其他用法:https://www.jianshu.com/p/d08e255312f9@Data
@Builder
public class User implements Serializable {
private static final long serialVersionUID = -1602774207630314992L;
private Integer id;
private String username;
private String password;
}