You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何结合PassengerBuilder与TripBuilder实现复杂对象图的计算表达式构建

结合PassengerBuilder与TripBuilder构建嵌套对象图

咱们一步一步来实现这个需求,先从基础的类型定义开始,再分别构建两个Computation Expression Builder,最后完成嵌套使用的逻辑。

首先明确核心的记录类型,定义好Passenger和Trip的结构:

type Trip = {
    Destination: string
    DepartureDate: DateTime
    Duration: int // 行程天数
}

type Passenger = {
    Name: string
    Age: int
    Trips: Trip list
}

接下来先实现TripBuilder,用自定义操作让行程配置的语法更直观:

type TripBuilder() =
    // 初始化空的Trip状态
    member _.Yield(_) = { Destination = ""; DepartureDate = DateTime.MinValue; Duration = 0 }
    
    // 自定义操作:设置目的地
    [<CustomOperation("destination")>]
    member _.SetDestination(trip, dest) = { trip with Destination = dest }
    
    // 自定义操作:设置出发日期
    [<CustomOperation("departureDate")>]
    member _.SetDepartureDate(trip, date) = { trip with DepartureDate = date }
    
    // 自定义操作:设置行程时长
    [<CustomOperation("duration")>]
    member _.SetDuration(trip, days) = { trip with Duration = days }

// 创建TripBuilder实例,方便后续使用
let trip = TripBuilder()

然后是核心的PassengerBuilder,重点要实现能嵌入TripBuilder计算表达式的操作,把构建好的Trip关联到Passenger上:

type PassengerBuilder() =
    // 初始化空的Passenger状态
    member _.Yield(_) = { Name = ""; Age = 0; Trips = [] }
    
    // 自定义操作:设置乘客姓名
    [<CustomOperation("name")>]
    member _.SetName(passenger, name) = { passenger with Name = name }
    
    // 自定义操作:设置乘客年龄
    [<CustomOperation("age")>]
    member _.SetAge(passenger, age) = { passenger with Age = age }
    
    // 核心操作:添加单个行程,直接接收TripBuilder的计算表达式
    [<CustomOperation("addTrip")>]
    member _.AddSingleTrip(passenger, tripExpr) =
        let builtTrip = tripExpr // 执行Trip的计算表达式,得到完整Trip实例
        { passenger with Trips = builtTrip :: passenger.Trips }
    
    // 可选扩展:批量添加行程
    [<CustomOperation("addTrips")>]
    member _.AddMultipleTrips(passenger, tripExprs) =
        let builtTrips = tripExprs |> List.map (fun expr -> expr)
        { passenger with Trips = builtTrips @ passenger.Trips }

// 创建PassengerBuilder实例
let passenger = PassengerBuilder()

现在你就能用想要的流畅语法来构建带行程的Passenger记录了:

let alice = passenger {
    name "Alice"
    age 30
    addTrip (trip {
        destination "Paris"
        departureDate (DateTime(2024, 7, 1))
        duration 7
    })
    addTrip (trip {
        destination "Tokyo"
        departureDate (DateTime(2024, 10, 15))
        duration 10
    })
}

// 验证结果
printfn "%A" alice

关键细节说明

  • 两个Builder都通过Yield方法初始化空的记录状态,再通过自定义操作逐步修改状态,符合Computation Expression的设计逻辑
  • PassengerBuilder的addTrip操作直接接收TripBuilder的计算表达式,执行后就能得到完整的Trip实例,再把它追加到Passenger的Trips列表中
  • 这种嵌套写法既保持了代码的可读性,又能灵活构建复杂的对象图

内容的提问来源于stack exchange,提问作者Fede

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 07:21:19