3

在许多情况下,能够通过其名称作为字符串设置/获取记录字段(例如,将记录转换为/从命令行参数、HTTP 标头、SQL 查询结果或将小部件存储在 GUI 树中)会很有用在易于使用的记录等中)。函数可以有类型

setField::String->Val->Record->Record
getField::String->Record->Val
getFieldNames::Record->[String]

其中 Val 可能是可以转换为其他类型的东西(字符串、glib GValue,甚至是我在此处描述的可转换对象)

我已经开始编写一个这样做的库,并计划将其贡献给社区(它需要一些 GHC 扩展,可能包括 TemplateHaskell)......

我的问题-这样的东西已经存在了吗?有没有更好的方法从外部名称/值对填充记录?我找遍了,找不到。(镜头是相关的,但不要使用字符串名称)。

我认为这会很有用,但不想重新发明轮子。

4

1 回答 1

3

您可能会使用 来执行类似的操作Vinyl,尽管您仍然需要创建强类型访问器。优点是类型系统包含足够的信息,以确保您永远不需要运行时处理Maybe-wrapped 查找失败。

从该链接复制一些相关示例

name     = Field :: "name"     ::: String
age      = Field :: "age"      ::: Int
sleeping = Field :: "sleeping" ::: Bool


jon = name =: "jon"
  <+> age =: 20
  <+> sleeping =: True

type LifeForm = ["name" ::: String, "age" ::: Int, "sleeping" ::: Bool]

jon :: PlainRec LifeForm

wakeUp :: (("sleeping" ::: Bool) ∈ fields) => PlainRec fields -> PlainRec fields
wakeUp = sleeping `rPut` False

jon' = wakeUp jon

> rGet name jon'
"jon"
> rGet sleeping jon
True
> rGet sleeping jon'
False

如果您不愿意做类似的事情,那么您可能会以某种运行时失败告终,这意味着您还不如拥有type Record = Map String Val.

于 2013-11-06T23:28:02.810 回答