Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/haskell/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
识别Haskell中的递归/嵌套类型(如类型同义词) 简短问题(已编辑):_Haskell_Recursion_Types_Type Synonyms - Fatal编程技术网

识别Haskell中的递归/嵌套类型(如类型同义词) 简短问题(已编辑):

识别Haskell中的递归/嵌套类型(如类型同义词) 简短问题(已编辑):,haskell,recursion,types,type-synonyms,Haskell,Recursion,Types,Type Synonyms,是否可以定义函数的类型签名,以便它接受具有任意深度的嵌套类型?我在寻找类型同义词(不是newtype)的行为,但要识别嵌套/递归类型 例如,定义为f::NestedList a->b的函数应该能够通过[a],[[a]],[[a]]]调用。。。等等 长问题(原件): 由于在Haskell中不可能将类型同义词与递归类型一起使用,因此有没有解决以下问题的方法 我需要一个同义词,如NestedList a,它将标识[a],[[a]],[[a]]。。。等等,在函数类型定义中。需要实现的功能示例如下:

是否可以定义函数的类型签名,以便它接受具有任意深度的嵌套类型?我在寻找类型同义词(不是newtype)的行为,但要识别嵌套/递归类型

例如,定义为
f::NestedList a->b
的函数应该能够通过
[a]
[[a]]
[[a]]]
调用。。。等等

长问题(原件): 由于在Haskell中不可能将类型同义词与递归类型一起使用,因此有没有解决以下问题的方法

我需要一个同义词,如
NestedList a
,它将标识
[a]
[[a]]
[[a]]
。。。等等,在函数类型定义中。需要实现的功能示例如下:

   flatten :: NestedList a -> [a]
显示了使用MultiParamTypeClasses语言扩展的
flant
解决方案,但它并没有特别解决我的问题。我需要在类之外定义函数

编辑:

flatte
只是函数定义的一个示例,我对函数本身不感兴趣。我需要一种机制来定义一个带有
嵌套列表a
的函数,并使用
[[a]]
[[a]]]
之类的参数来调用它,而不需要额外的类型构造函数、get方法等。正如标题中所建议的,我需要一种行为类似于嵌套列表上的类型同义词的东西,主要用于为在
[…[a]]
上工作的函数提供类型签名,同时确保基本类型为
a


根据Haskell的强类型系统,这是不可能的,并揭示了原因。我只是想问,是否有类似宏/同义词的机制或解决方法,或者允许我这样做的语言扩展。

您是否正在寻找类似的工具

data NestedList a = List [NestedList a] | Element a

flatten :: NestedList a -> [a]
flatten (Element x) = [x]
flatten (List xs)   = concatMap flatten xs
编辑 正如用户2407038所建议的,如果您有兴趣使用文件顶部的
Foldable
(包括
{-#LANGUAGE DeriveFoldable#-}
导入数据.Foldable
)GHC扩展名,您可以这样做

data NestedList a = List [NestedList a] | Element a deriving (Foldable)
还有一个名为
toList
的函数已经在
Foldable
中定义,它将产生与上面的
flatten
相同的输出

编辑2 以下是有关更新问题的其他有趣内容。理想情况下,能够用

instance (Foldable t, Functor t, Foldable t') => Foldable (t . t')
其中
(t.t')a
t(t'a)
(一种类型级组合)的类型同义词。这显然不起作用,我倾向于认为有一个合乎逻辑的解释,为什么引入这一点会从根本上打破Haskell,但我想不出来。然而,有一个名为的包定义了类似的东西(除了我们想要一个
类型
同义词,而不是
新类型

这让我们可以编写以下内容:

toList $ (O) [[1,2,3,4],[4,5,6]]
toList $ (O . O) [[[1],[2,3,4]],[[4],[5,6]]]
toList $ (O . O . O) [[[[1]],[[2,3],[4]]],[[[4]],[[5,6]]]]

这也很有趣。

你在找这样的东西吗

data NestedList a = List [NestedList a] | Element a

flatten :: NestedList a -> [a]
flatten (Element x) = [x]
flatten (List xs)   = concatMap flatten xs
编辑 正如用户2407038所建议的,如果您有兴趣使用文件顶部的
Foldable
(包括
{-#LANGUAGE DeriveFoldable#-}
导入数据.Foldable
)GHC扩展名,您可以这样做

data NestedList a = List [NestedList a] | Element a deriving (Foldable)
还有一个名为
toList
的函数已经在
Foldable
中定义,它将产生与上面的
flatten
相同的输出

编辑2 以下是有关更新问题的其他有趣内容。理想情况下,能够用

instance (Foldable t, Functor t, Foldable t') => Foldable (t . t')
其中
(t.t')a
t(t'a)
(一种类型级组合)的类型同义词。这显然不起作用,我倾向于认为有一个合乎逻辑的解释,为什么引入这一点会从根本上打破Haskell,但我想不出来。然而,有一个名为的包定义了类似的东西(除了我们想要一个
类型
同义词,而不是
新类型

这让我们可以编写以下内容:

toList $ (O) [[1,2,3,4],[4,5,6]]
toList $ (O . O) [[[1],[2,3,4]],[[4],[5,6]]]
toList $ (O . O . O) [[[[1]],[[2,3],[4]]],[[[4]],[[5,6]]]]

这也很有趣。

或者只是
数据嵌套列表a=List[NestedList a]|元素a派生可折叠的
。确实,您的解决方案可以使用
展平
,但这不是我想要实现的。我想我不是很具体,我会修改我的问题。问题是我不能交替使用
[[[Int]]]
嵌套列表Int
,即使用
[[[Int]]]]
调用函数。这就是为什么我想要类似于类型同义词的东西。@GeorgeUngureanu我明白了。我不认为你会发现类型同义词
Datalist a
适用于
[a]
[[a]]
等。因为这意味着
[a]=Datalist a=[[a]]
,但这显然是不正确的。@Alec:绝对正确!哈斯克尔确实不允许这样做。但是以应用方式实现的函数可以完美地与
[a]
[a]
等一起工作。我只需要给该函数一个类型签名(同时仍然确保基类型是
a
),或者只需
数据嵌套列表a=List[NestedList a]|元素a派生可折叠的
,您的解决方案确实适用于展平,但这不是我想要实现的。我想我不是很具体,我会修改我的问题。问题是我不能交替使用
[[[Int]]]
嵌套列表Int
,即使用
[[[Int]]]]
调用函数。这就是为什么我想要类似于类型同义词的东西。@GeorgeUngureanu我明白了。我认为您不会发现类型同义词
Datalist a
适用于
[a]
[[a]]
等,因为这意味着
[a]=Datalist a