![](/img/trans.png)
[英]F# - Cleanest way to Extract/Unwrap an Expected Case's Typed Value from Discriminated Union?
[英]how to unwrap union value in list in f#
您知道要解开单个联合类型的值,您必须这样做:
type Foo = Foo of int*string
let processFoo foo =
let (Foo (t1,t2)) = foo
printfn "%A %A" t1 t2
但我的问题是:如果有办法为列表做到这一点?:
let processFooList (foolist:Foo list ) =
let ??? = foolist // how to get a int*string list
...
谢谢。
最好的方法是使用一个与List.map
结合的函数
let processFooList (foolist:Foo list ) = foolist |> List.map (function |Foo(t1,t2)->t1,t2)
没有用于将列表从Foo
转换为int * string
的预定义活动模式,但您可以将命名模式§7.2 (解构单例并集)与投影组合到您自己的单例ActivePattern§7.2.3中 。
let asTuple (Foo(t1, t2)) = t1, t2 // extract tuple from single Foo
let (|FooList|) = List.map asTuple // apply to list
用作函数参数:
let processFooList (FooList fooList) = // now you can extract tuples from Foo list
... // fooList is an (int * string) list
用于绑定:
let (FooList fooList) =
[ Foo(1, "a"); Foo(2, "b") ]
printfn "%A" fooList // prints [(1, "a"); (2, "b")]
提炼/总结/重述/重新发布其他两个答案,您的引用行:
let ??? = foolist // how to get a int*string list
可以变成:
let ``???`` = foolist |> List.map (function |Foo(x,y) -> x,y)
如果您正在编写转换,则可以使用以下任一方法在已定义活动模式的参数中进行匹配:
let (|FooList|) = List.map <| fun (Foo(t1, t2)) -> t1,t2
let (|FooList|) = List.map <| function |Foo(t1, t2) -> t1,t2
然后可以按如下方式消费:
let processFooList (fooList:Foo list ) =
// do something with fooList
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.