C# 如何在fluent接口的方法调用中构建序列

C# 如何在fluent接口的方法调用中构建序列,c#,dsl,fluent,fluent-interface,C#,Dsl,Fluent,Fluent Interface,嗨,我想建立一个流畅的界面,用于创建某种工厂或建设者的am对象 我知道我必须“返回这个”以使方法可链接 public class CarBuilder { public CarBuilder() { car = new Car(); } private Car car; public CarBuilder AddEngine(IEngineBuilder engine) { car.Engine = engine.En

嗨,我想建立一个流畅的界面,用于创建某种工厂或建设者的am对象

我知道我必须“返回这个”以使方法可链接

public class CarBuilder
{

   public  CarBuilder()
   {
       car = new Car();
   }
    private Car car;

    public CarBuilder AddEngine(IEngineBuilder engine)
    {
        car.Engine = engine.Engine();
        return this;
    }

    public CarBuilder AddWheels(IWheelsBuilder wheels)
    {
        car.Wheels = wheels.Wheels();
        return this;
    }
    public CarBuilder AddFrame(IFrameBuilder frame)
    {
        car.Frame = frame.Frame();
        return this;
    }

    public Car BuildCar()
    {
        return car;
    }

}
有了这个,我可以造一辆这样的车:

 Car c = builder.AddFrame(fBuilder).AddWheels(wBuilder).AddEngine(eBuilder).BuildCar();
但我需要的是一个特殊的序列或工作流程: 我只能在车架顶部制造车轮,当车轮存在时,我就能制造发动机。 因此,我不想提供汽车制造商的每一种方法,而是希望能够只向制造商添加车架,然后只向车架添加车轮,然后在车架上添加发动机

如果EngineBuilder本身有一个像eBuilder.Cycles(12).With活塞()这样流畅的api,那么它将是一个什么样的好实现呢

有可能有这样的东西吗

Car c = builder.AddFrame(fBuilder).AddWheels(wBuilder).AddEngine(x=>x.WithCylinders(12).WithPistons()).BuildCar();

总之,如何构造fluent接口的流程以及如何嵌套fluent接口?

那么,添加轮子不是属于框架的方法吗?您还可以考虑在请求无效操作时引发异常,例如添加没有框架的轮子。

与使用单个CarBuilder类公开所有方法不同,您可以使用多个类,每个类只公开适合于正在构建的汽车“状态”的方法

举个例子,
CarBuilder
只提供
AddFrame
AddFrame
返回一个只提供
AddWheels
的类
CarBuilderWithFrame
的对象,而不是返回
this
,它返回一个只提供
AddEngine
的类
CarBuilderWithFrameAndWheels
的对象,它返回一个类为
carbuilder的对象,其中包含仅提供
Build
的所有内容

这个例子是非常连续的,你可以争论,对于这样一个线性过程,做这么多的工作是否有意义

我喜欢的一个例子是印刷。打印机对象可以返回PrintJob对象,该对象提供三种方法:取消、打印或开始页面。StartPage方法将返回一个Page对象,该对象为您提供所有绘图命令的方法,一个称为EndPage的对象将返回PrintJob对象。这使得硬编码一个简单的打印作业变得容易

Printer.StartPrintJob().StartPage().DrawText("Title").DrawIcon("logo.png").EndPage().Print();

我想创建一个像fluent nhibernate一样的fluent API和Costam dsl。。。更像是链接方法