通过lombok@Builder注解理解BUILDER(生成器)设计模式
意图
将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。
适用性
在以下情况使用Builder模式
- 当创建复杂对象的算法应该独立与该对象的组成部分以及它们的装配方式时。
- 当构造过程必须允许被构造的对象有不同的表示时。
Builder设计模式中涉及到的参与者
- Builder
——为创建一个Product对象的各个部件指定抽象接口。 - ConcreteBuilder
——实现Builder的接口以构造和装配该产品的个部件。
——定义并明确它所创建的表示。
——提供一个检索产品的接口。 - Director
——构造一个使用Builder接口的对象。 - Product
——表示被构造的复杂对象。ConcreteBuilder创建该产品的内部表示并定义它的装配过程。
——包含定义组成部件的类,包括将这些部件装配成最中产品的接口。
其实,在实际使用时,可以根据需要对参与者进行简化或删减,最小结构应该至少包括Builder和Product。
最小结构的Builder模式代码范例-Java
package com.wongoing.entity;
/**
* 功能说明:参与者Product
* 修改说明:
* @author zheng
* @date 2020年11月10日 上午11:08:39
* @version 0.1
*/
public class User {
private int id;
private String name;
private String sex;
public User() {}
public User(int id, String name, String sex) {
this.id = id;
this.name = name;
this.sex = sex;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public String getSex() {
return sex;
}
public void setSex(String sex) {
this.sex = sex;
}
public static UserBuilder builder() {
return new UserBuilder();
}
/**
* 功能说明:参与者Builder(用于创建一个User对象的各个部件的类)
* 修改说明:
* @author zheng
* @date 2020年11月10日 上午11:07:06
* @version 0.1
*/
public static class UserBuilder {
private int id;
private String name;
private String sex;
public UserBuilder id(int id) {
this.id = id;
return this;
}
public UserBuilder name(String name) {
this.name = name;
return this;
}
public UserBuilder sex(String sex) {
this.sex = sex;
return this;
}
public User build() {
return new User(this.id, this.name, this.sex);
}
public String toString() {
return "User.UserBuilder(id = " + this.id + ", name = " + this.name + ", sex = " + this.sex + ")";
}
}
}
测试代码如下:
package com.wongoing.entity.test;
import org.junit.Test;
import com.wongoing.entity.User;
public class UserTest {
@Test
public void testUser() {
User user = User.builder().id(1).name("Lisa").sex("女").build();
System.out.println(user.getId());
System.out.println(user.getName());
System.out.println(user.getSex());
}
}
使用了lombok的注解后的代码
package com.wongoing.entity;
import lombok.AllArgsConstructor;
import lombok.Builder;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* 功能说明:参与者Product
* 修改说明:
* @author zheng
* @date 2020年11月10日 上午11:08:39
* @version 0.1
*/
@Data //生成getter,setter等函数
@NoArgsConstructor //生成全参数构造函数
@AllArgsConstructor //生成无参数构造函数
@Builder //实现Builder设计模式
public class User {
private int id;
private String name;
private String sex;
}
测试代码不变还是
package com.wongoing.entity.test;
import org.junit.Test;
import com.wongoing.entity.User;
public class UserTest {
@Test
public void testUser() {
User user = User.builder().id(1).name("Lisa").sex("女").build();
System.out.println(user.getId());
System.out.println(user.getName());
System.out.println(user.getSex());
}
}
另附最小结构的Builder模式代码范例-C#
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
namespace Wongoing.Entity
{
/// <summary>
/// 参与者Product
/// </summary>
public class User
{
private int id;
private string name;
private string sex;
public User()
{
}
public User(int id, string name, string sex)
{
this.id = id;
this.name = name;
this.sex = sex;
}
public int Id
{
get { return id; }
set { id = value; }
}
public string Name
{
get { return name; }
set { name = value; }
}
public string Sex
{
get { return sex; }
set { sex = value; }
}
public static UserBuilder Builder
{
get
{
return new User.UserBuilder();
}
}
/// <summary>
/// 参与者Builder(用于创建一个User对象的各个部件的类)
/// </summary>
public class UserBuilder
{
private int id;
private string name;
private string sex;
public UserBuilder()
{
}
public UserBuilder Id(int id)
{
this.id = id;
return this;
}
public UserBuilder Name(string name)
{
this.name = name;
return this;
}
public UserBuilder Sex(string sex)
{
this.sex = sex;
return this;
}
public User Build()
{
return new User(this.id, this.name, this.sex);
}
public override string ToString()
{
return "User.UserBuild(Id = " + this.id + ", Name = " + this.name + ", Sex = " + this.sex + ")";
}
}
}
}
测试代码如下:
using System;
using Microsoft.VisualStudio.TestTools.UnitTesting;
namespace Wongoing.Entity.UTest
{
[TestClass]
public class UserTest
{
[TestMethod]
public void TestUser()
{
Wongoing.Entity.User user = Wongoing.Entity.User.Builder.Id(1).Name("Lisa").Sex("女").Build();
Console.WriteLine(user.Id);
Console.WriteLine(user.Name);
Console.WriteLine(user.Sex);
}
}
}