【发布时间】:2019-03-02 16:58:41
【问题描述】:
我想创建一个给定函数类型(例如String -> Nat -> Bool)的函数,它将返回对应于该函数类型的类型列表(例如[String, Nat, Bool])。大概这样一个函数的签名是Type -> List Type,但我正在努力确定它是如何实现的。
【问题讨论】:
标签: idris
我想创建一个给定函数类型(例如String -> Nat -> Bool)的函数,它将返回对应于该函数类型的类型列表(例如[String, Nat, Bool])。大概这样一个函数的签名是Type -> List Type,但我正在努力确定它是如何实现的。
【问题讨论】:
标签: idris
我不相信一般情况下可以这样做,因为您无法在功能上进行模式匹配。你也不能检查函数的类型。这不是依赖类型的意义所在。就像在 Haskell 或 OCaml 中一样,您实际上可以对函数做的唯一事情就是将其应用于某个参数。但是,我设计了一些可能会做的技巧:
myFun : {a, b : Type} -> (a -> b) -> List Type
myFun {a} {b} _ = [a, b]
现在的问题是a -> b 是唯一可以匹配任意函数的签名。但是,对于数量大于 1 的函数,它的行为当然不会像您希望的那样:
> myFun (+)
[Integer, Integer -> Integer] : List Type
因此需要对自身进行某种递归调用以提取更多参数类型:
myFun : {a, b : Type} -> (a -> b) -> List Type
myFun {a} {b} _ = a :: myFun b
这里的问题是b 是任意类型,不一定是函数类型,我无法动态检查它是否是函数,所以我想这和你一样多可以和伊德里斯一起做。
然而,动态检查类型(至少在我看来)并不是静态类型语言所需要的功能。毕竟静态类型的全部意义在于提前指定函数可以处理什么样的参数,并防止在编译时调用带有无效参数的函数。所以基本上你可能根本不需要它。如果您指定了更宏伟的目标,那么有人可能会向您展示正确的做法。
【讨论】:
(+) 调用myFun 会有些奇怪,因为它的类型是Integer -> Integer -> Integer,这不是真的。然而,基本上,函数根本不可能表现得适合多态函数。