Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/list/4.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
List 如何修复代码中的错误(';无法构造无限类型';),以及如何使代码正常工作_List_Haskell - Fatal编程技术网

List 如何修复代码中的错误(';无法构造无限类型';),以及如何使代码正常工作

List 如何修复代码中的错误(';无法构造无限类型';),以及如何使代码正常工作,list,haskell,List,Haskell,基本上,我试着做一个函数,给你一个列表和一个数字,你必须把列表分割成与给定数字相同大小的列表,最后一次分割的长度可以小于给定的数字 separa a xs = if length xs >= a then separaM a (drop a xs) ([take a xs]) else [xs] separaM a xs yss = if length xs >= a then separaM a (drop a xs) (yss : (take a xs)) else separ

基本上,我试着做一个函数,给你一个列表和一个数字,你必须把列表分割成与给定数字相同大小的列表,最后一次分割的长度可以小于给定的数字

separa a xs = if length xs >= a then separaM a (drop a xs) ([take a xs]) else [xs]

separaM a xs yss = if length xs >= a then separaM a (drop a xs) (yss : (take a xs)) else separaM a [] (yss : xs)
separaM a [] yss = yss

我希望3个“comovais”的输出为[“com”、“ova”、“is”],但在我的程序中,由于错误而没有输出

您的代码中有一些错误。调整对
(:)
的误用,使其通过类型检查:

separa a xs 
  | length xs >= a =  go a (drop a xs) [take a xs]
  | otherwise      =  [xs]
  where
  go a xs yss 
    | length xs >= a  =  go a (drop a xs) (yss ++ [take a xs]) 
                                  -- was: (yss : (take a xs))
    | otherwise       =  go a [] (yss ++ [xs])
                         -- was: (yss : xs)
  go a [] yss = yss
但最好进一步改为

separa :: Int -> [a] -> [[a]]
separa a xs 
  | length xs >= a =  go a (drop a xs) [take a xs]
  | otherwise      =  [xs]
  where
  go a xs yss 
    | length xs >= a  =  go a (drop a xs) ([take a xs] ++ yss) 
    | otherwise       =  reverse ([xs] ++ yss)
它的工作原理是:

> separa 3 [1..10]
[[1,2,3],[4,5,6],[7,8,9],[10]]
这是一种常见的“反向构建,然后在构建时反向构建”的习惯用法,在严格的函数式语言中很常见。其中一些允许通过称为尾部递归模cons的技术,以自顶向下的自然顺序构建列表。Haskell是懒惰的,它让我们以自上而下的方式自然轻松地构建它的列表,并使用等效的保护递归:

这里有一个由一个关闭的错误;我把它留给你自己解决


但有时无限类型是问题固有的,而不是编程错误的结果。然后我们可以通过使用递归类型来修复它

每当我们得到类型等价性
t~a..b..t..c..
,我们就可以从定义类型开始

newtype T = MkT (a..b..T..c..)
然后查看哪些类型变量是自由的,并关闭它们,如图所示

newtype T a b c = MkT (a..b..(T a b c)..c..)

例如:

请注意表达式:

yss : (take a xs)
(以xs为例)
具有类型
[b]
,因此
yss
具有类型
b
。但是当您将
yss:(使用xs)
作为
separaM
函数的参数传递时,
yss
应具有类型
[b]
而不是
b
。这就是发生错误的原因

实际上,您不需要
yss
来存储结果,递归函数可以定义为:

separaM _ [] = []
separaM a xs = (if length xs >= a then (take a xs) else xs) : 
               separaM a (drop a xs)
separaM _ [] = []
separaM a xs = (if length xs >= a then (take a xs) else xs) : 
               separaM a (drop a xs)