Elm 中的通用模式匹配
Generic pattern matching in Elm
我正在尝试构建一个通用映射函数,该函数将从联合类型中提取可能的内部类型,对内部值应用转换并将其映射回外部类型。
问题是,我需要一种方法来区分外部类型的特定值是否具有内部类型。
如果下面的代码实际编译了,它对我有用,但 Elm 不允许在模式匹配中使用常量。 (constructor
第4行编译失败)
还有其他方法可以做到吗?
map : (inner -> outer) -> (inner -> inner) -> outer -> outer
map constructor func current =
case current of
constructor child ->
constructor (func child)
_ ->
current
不,不幸的是 Elm 没有办法通用地表达这种东西,你需要为每个自定义类型编写一个特定的版本。
你可以看看 elm-accessors
图书馆。有了它,您将需要为您的每个类型构造函数定义一个 Relation
(这非常简单)。但是之后你就可以自由地使用一个很好的旧 List.map
来映射任何构造函数!
这是一个用法示例:
type FooBar a b
= Foo a
| Bar b
items =
List.map
(over (foo << try) ((+) 1) -- affects only "Foo"s
<<
over (bar << try) (\b -> b ++ "!")) -- affects only "Bar"s
[Foo 1, Bar "a", Foo 10]
-- = [Foo 2,Bar "a!",Foo 11]
我正在尝试构建一个通用映射函数,该函数将从联合类型中提取可能的内部类型,对内部值应用转换并将其映射回外部类型。
问题是,我需要一种方法来区分外部类型的特定值是否具有内部类型。
如果下面的代码实际编译了,它对我有用,但 Elm 不允许在模式匹配中使用常量。 (constructor
第4行编译失败)
还有其他方法可以做到吗?
map : (inner -> outer) -> (inner -> inner) -> outer -> outer
map constructor func current =
case current of
constructor child ->
constructor (func child)
_ ->
current
不,不幸的是 Elm 没有办法通用地表达这种东西,你需要为每个自定义类型编写一个特定的版本。
你可以看看 elm-accessors
图书馆。有了它,您将需要为您的每个类型构造函数定义一个 Relation
(这非常简单)。但是之后你就可以自由地使用一个很好的旧 List.map
来映射任何构造函数!
这是一个用法示例:
type FooBar a b
= Foo a
| Bar b
items =
List.map
(over (foo << try) ((+) 1) -- affects only "Foo"s
<<
over (bar << try) (\b -> b ++ "!")) -- affects only "Bar"s
[Foo 1, Bar "a", Foo 10]
-- = [Foo 2,Bar "a!",Foo 11]