, "unit → " a " Bind, ( , monad/computation).
, . : , ( return). seq<option<'a>>. , . None, , Some(value), , return.
- Bind. , , , ( let! a = 1), . :
let foo() = stepwise {
return 1; }
let bar() = stepwise {
let! a = foo()
return a + 10 }
, , . , , Bind return , :
type Stepwise() =
member x.Bind(v:seq<option<_>>, rest:(_ -> seq<option<_>>)) = seq {
let en = v.GetEnumerator()
let nextVal() =
if en.MoveNext() then en.Current
else failwith "Unexpected end!"
let last = ref (nextVal())
while Option.isNone !last do
yield None
last := next()
yield None
yield! rest (Option.get !last) }
member x.Return v = seq {
yield Some(v) }
let stepwise = Stepwise()
let one v = stepwise.Return(v)
:
let oneStep = stepwise {
let! y = one( "foo" )
printfn "got: %A" y
return y + "bar" }
let threeSteps = stepwise {
let! x = oneStep
printfn "got: %A" x
let! y = one( x + "third" )
printfn "got: %A" y
return "returning " + y }
, , , F # for. :
for step, idx in Seq.zip threeSteps [ 1 .. 10] do
printf "STEP %d: " idx
match step with
| None _ -> ()
| Some(v) -> printfn "Final result: %s" v
, !
PS: ! , (http://tomasp.net/blog)? !