我该如何阅读如下的类型定义?
type Config data msg =
Config
{ toId : data -> String
, toMsg : State -> msg
, columns : List (ColumnData data msg)
, customizations : Customizations data msg
}
Run Code Online (Sandbox Code Playgroud)
似乎有一个"重复"元素:配置存在于LHS和RHS上.
另一个例子是:
type State =
State String Bool
Run Code Online (Sandbox Code Playgroud)
这些类型的声明通信是什么?
左侧命名您要创建的类型.在右侧,您将定义类型实际可以采用的值.可能只有一个或多少你想要的.
type MyType = ValueA | ValueB | ValueC
Run Code Online (Sandbox Code Playgroud)
此外,您可以创建其值包含额外数据的类型.这可以通过遵循另一种类型的值名称(在形式上称为数据构造函数或Elm中的变体)来完成.您可以使用任何具体类型并具有任意数量.变体之间的类型和arities(参数数量)不需要相同.
type MyType = ValueA String | ValueB Int (List String) | ValueC
Run Code Online (Sandbox Code Playgroud)
这些都是具体类型.当你有一个值时,它将始终具有一个具体的类型.假设您要创建自己的对类型.你可以定义
type PairOfIntAndInt = PairOfIntAndInt Int Int
type PairOfIntAndString = PairOfIntAndString Int String
type PairOfStringAndString = PairOfStringAndString String String
…
Run Code Online (Sandbox Code Playgroud)
但这不会很方便.因此,Elm允许您使用参数获得类型构造函数(即LHS上类型名称的正式名称).它们将以小写字母书写:
type Pair first second = Pair first second
Run Code Online (Sandbox Code Playgroud)
许多有用的核心功能,例如Maybe
或Result
实际上是接受参数的类型.它们也被称为抽象类型.要使它们成为具体类型,您需要将具体类型[^ 1]传递给每个参数.
现在,让我们看看你的代码.你有一个带有Config
两个参数的类型构造函数.
type Config data msg =
Run Code Online (Sandbox Code Playgroud)
并且该类型接受使用其一个数据构造函数创建的值
Config
Run Code Online (Sandbox Code Playgroud)
它存储单个值.值的类型实际上是组合类型,记录.它期望四个字段及其类型将取决于类型构造函数的参数.
{ toId : data -> String
, toMsg : State -> msg
, columns : List (ColumnData data msg)
, customizations : Customizations data msg
}
Run Code Online (Sandbox Code Playgroud)
例如,如果您有一个具体的类型Config String Int
,它将期望以下值:
Config
{ toId = someToIdValue
, toMsg = someToMsgValue
, columns = someColumnsValue
, customizations = someCustomizationsValue
}
Run Code Online (Sandbox Code Playgroud)
其中,someToIdValue
将必须的功能回吐String
并返回String
,toMsg
功能从State
到Int
,等等.
有关详细信息,请参阅https://guide.elm-lang.org/types/custom_types.html
[^ 1]:像Haskell这样的语言实际上允许更狂野的类型.https://wiki.haskell.org/Kind