c# - 为什么我们需要构建器设计模式而不是模型?
问题描述
下面是我对builder设计模式的理解。假设我们有一个 Product 类,如下所示。
public class Product
{
public string Name { get; set; }
public string Description { get; set; }
public int NumberOfProducts { get; set; }
public decimal Price { get; set; }
public bool IsDurable { get; set; }
}
构建器界面:
public interface IBuilder
{
void SetName(string value);
void SetPrice(decimal value);
void SetIsDurable(bool value);
void SetNumberOfProducts(int value);
void SetDescription(string value);
Product GetProduct();
}
具有 setter 方法并获取产品对象的具体构建器。
public class ConcreteBuilder : IBuilder
{
Product product = new Product();
public Product GetProduct()
{
return product;
}
public void SetDescription(string value)
{
product.Description = value;
}
public void SetIsDurable(bool value)
{
product.IsDurable = value;
}
public void SetName(string value)
{
product.Name = value;
}
public void SetNumberOfProducts(int value)
{
product.NumberOfProducts = value;
}
public void SetPrice(decimal value)
{
product.Price = value;
}
}
在现实世界的场景中,产品的属性应该从用户输入中填充,而不是像这样硬编码。在这种情况下,我们还需要发送产品来构造产品对象。
public Product ConstructProduct(IBuilder builder)
{
builder.SetDescription("P");
builder.SetIsDurable(false);
builder.SetName("My Name");
builder.SetPrice(10);
builder.SetNumberOfProducts(5);
return builder.GetProduct();
}
在客户端使用builder对象,如下所示:
public class Client
{
public void AddProduct()
{
ConcreteBuilder builder = new ConcreteBuilder();
var builtProduct = new Director().ConstructProduct(builder);
Console.WriteLine(builtProduct.Description);
}
}
而不是使用上面所示的构建器模式,为什么我们不能使用 Product 模型类本身,如下所示,当在构造器中添加许多属性时(以避免伸缩构造反模式)?如果有任何可选属性,它们可以为空。
public class Client
{
Product _prod;
public Client(Product prod)
{
_prod = prod;
}
public void AddProduct()
{
// Code to add product
Console.WriteLine(_prod.Description);
}
}
解决方案
创建类时,主要目标是降低程序的复杂性。您创建一个类来隐藏复杂性,这样您就不需要考虑它。当然,你需要在编写课程时考虑它。但是在编写完之后,您应该能够忘记细节并在不了解其内部工作原理的情况下使用该类。
显然,在您在问题中提到的情况下,使用构建器模式会增加复杂性,仅使用模型是正确的选择。因为创建Product
对象的过程非常简单。
在其他情况下,创建对象可能是一项复杂的操作,您可以使用构建器设计模式来管理这种复杂性。
这是构建器模式在现实世界中的使用示例:https ://dzone.com/articles/builder-pattern-usage-real
推荐阅读
- swift - 是否有以编程方式添加/显示 UITabBar 的功能?
- google-apps-script - 有没有办法通过应用脚本在列中搜索值?
- python - 打开每个谷歌搜索结果python selenium的链接
- php - 如何将php字符串中的数字相加?
- go - 如何将 aws.WriteAtBuffer 转换为 io.Reader?
- reactjs - 将 2 HOC 添加到反应中的组件
- jquery - 全日历议程周中未显示列边框
- php - 我是否正确地尝试使用 PHP 更新数据库中的记录?
- php - 为什么这个 PHP 代码总是返回相同的回声?
- php - 保证工作被执行的最佳方式