构建器模式中构建器的创建

发布于 2024-10-25 23:42:07 字数 2072 浏览 1 评论 0原文

我想澄清我对构建器模式的使用,特别是如何创建构建器的类型。在示例中,它只是假设构建器的类型并创建它。但是,我在“ChartBuilderFactory”类中创建了一个 CreateBuilder 方法,该方法根据传递给它的某个对象返回构建器的类型。这是最好的方法吗?我已经发布了我的示例代码,并且希望有更好的设计的替代方案和建议。

class Program
{
    static void Main(string[] args)
    {
        DataObject data = new DataObject("basic", 2);

        ChartDirector director = new ChartDirector();
        ChartBuilderFactory builderFactory = new ChartBuilderFactory();
        ChartBuilder builder = builderFactory.CreateChartBuilder(data);
        director.Construct(builder);

        Console.WriteLine(builder.GetChart());
        Console.ReadKey();
    }
}

class ChartBuilderFactory
{
    public ChartBuilder CreateChartBuilder(DataObject data)
    {
        ChartBuilder builder;
        if (data.DataType == "basic")
            builder = new ChartBuilderBasic(data);
        else if (data.DataType == "vector")
            builder = new ChartBuilderVector(data);
        else
            builder = null;

        return builder;
    }
}           

class ChartDirector
{

    public void Construct(ChartBuilder builder)
    {
        builder.CreateChart();
        builder.LoadData();
    }
}

abstract class ChartBuilder
{
    protected string myChartObject = "";
    protected DataObject data;

    public ChartBuilder(DataObject data)
    {
        this.data = data;
    }

    abstract public void CreateChart();
    abstract public void LoadData();
    public string GetChart() { return myChartObject; } 
}

class ChartBuilderBasic : ChartBuilder
{
    public ChartBuilderBasic(DataObject data)
        : base(data) { }

    public override void CreateChart()
    {
        myChartObject = "MyBasicChart";
    }

    public override void LoadData()
    {
        myChartObject += Convert.ToString(data.Data);
    }
}

class ChartBuilderVector : ChartBuilder
{ /** Alternative Implementation here */ }

class DataObject
{
    /** Constructor and private member variables here */
    public string DataType { get { return this.dataType; } }
    public int Data { get { return this.data; } }
}

I want to clarify my use of the builder pattern, in particular how the type of builder is created. In examples, it just assumes the type of builder and creates it. However, I created a CreateBuilder method in a 'ChartBuilderFactory' class which returns the type of builder based on some object that was passed to it. Is this the best way of doing this? I've posted my sample code and would appreciate alternatives and suggestions for better design.

class Program
{
    static void Main(string[] args)
    {
        DataObject data = new DataObject("basic", 2);

        ChartDirector director = new ChartDirector();
        ChartBuilderFactory builderFactory = new ChartBuilderFactory();
        ChartBuilder builder = builderFactory.CreateChartBuilder(data);
        director.Construct(builder);

        Console.WriteLine(builder.GetChart());
        Console.ReadKey();
    }
}

class ChartBuilderFactory
{
    public ChartBuilder CreateChartBuilder(DataObject data)
    {
        ChartBuilder builder;
        if (data.DataType == "basic")
            builder = new ChartBuilderBasic(data);
        else if (data.DataType == "vector")
            builder = new ChartBuilderVector(data);
        else
            builder = null;

        return builder;
    }
}           

class ChartDirector
{

    public void Construct(ChartBuilder builder)
    {
        builder.CreateChart();
        builder.LoadData();
    }
}

abstract class ChartBuilder
{
    protected string myChartObject = "";
    protected DataObject data;

    public ChartBuilder(DataObject data)
    {
        this.data = data;
    }

    abstract public void CreateChart();
    abstract public void LoadData();
    public string GetChart() { return myChartObject; } 
}

class ChartBuilderBasic : ChartBuilder
{
    public ChartBuilderBasic(DataObject data)
        : base(data) { }

    public override void CreateChart()
    {
        myChartObject = "MyBasicChart";
    }

    public override void LoadData()
    {
        myChartObject += Convert.ToString(data.Data);
    }
}

class ChartBuilderVector : ChartBuilder
{ /** Alternative Implementation here */ }

class DataObject
{
    /** Constructor and private member variables here */
    public string DataType { get { return this.dataType; } }
    public int Data { get { return this.data; } }
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

稚气少女 2024-11-01 23:42:07

我认为您实际上想要的是使用工厂模式来创建生成器类。 Director 并不创建 Builder,但对它们具有依赖关系。

看看这个网站,它可以很好地洞察模式并使用一些真实的例子。

[编辑:基于修订后的问题]

现在您已经在工厂内创建了构建器,您就可以开始了。如果您想删除正确构建器的条件/发现,有许多选项,具体取决于系统的大小和复杂性。

  1. 如果构建器和数据类型的类型数量不会改变(或根本不会改变),请保持现有方式。
  2. 通过字典在构建器和类型之间建立映射。 (更复杂)见下文
  3. 或者通过读取数据类型与构建器类型之间映射的文件来完全驱动它通过配置。 (有点过分,但可能)

最后两个选项可能涉及反射(使用 Activator 类)以创建 Builder 类(或一些依赖注入容器,例如 unity),但确切的机制至少封装在 ChartBuilderFactory 中,

理想情况下,如果您使用依赖注入(控制反转),您将分离构建从对象的使用方式来看。如果你将其集中化,它就会变得更容易控制,甚至在以后需要时进行更改。更不用说让它更容易测试了。

I think you actually want is to use the Factory pattern to create the Builder classes. The Director does not create the Builder but has the dependency on them.

Have a look at this site which gives a good insight into patterns and uses some real example.

[EDIT : based on revised question]

Now that you have the creating of the Builders inside a factory you are set to go. If you want to remove the condition / finding of the correct builder there are a number of options depending on the size and complexity of the system.

  1. Leave it the way you have it if the number of types of builder and data types will not change (or much at all)
  2. Have a mapping between the builder and type through a dictionary. (more complex) see below
  3. Or completely drive it through configuration by reading a file that maps between the type of data to the type of builder. (going a bit overboard but possible)

The last 2 options might involve reflection (using the Activator class) in order to create the Builder class (or some Dependency Injection containers such as unity), but the exact mechanics are at least encapsulated inside the ChartBuilderFactory

Ideally if you use Dependency Injection (Inversion of Control) you are separating the construction of the objects from the way they are used. And if you centralize this it becomes easier to control and even change later if you need to. Not to mention making it easier to test.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文