简体   繁体   English

Haskell无法构造无限类型:a0 = [a0]

[英]Haskell cannot construct the infinite type: a0 = [a0]

I am attempting to solve the second problem on Project Euler using Haskell. 我正在尝试使用Haskell解决有关Euler项目的第二个问题。 The problem is fairly straight forward - sum the even fibonacci numbers less then 4000000. (Me being OCD, I'm implimenting a slightly modified function - one which allows an arbitraty limit). 问题是很直接的-将偶数斐波纳契数相加小于4000000。(我是OCD,我暗示的是略作修改的函数-允许任意限制的函数)。

My initial code was: 我的初始代码是:

euler2 limit (num1:num2) 
    |(num1>limit) = 0
    |((num2>limit) && ((mod num1 2) == 0)) = num1
    |(num2>limit) = 0
    |(((mod num1 2) == 0) && ((mod num2 2) == 0)) = num1+num2+(euler2 limit [num1+num2,num1+num2+num2])
    |((mod num1 2) == 0) = num1+(euler2 limit [num1+num2,num1+num2+num2])
    |((mod num2 2) == 0) = num2+(euler2 limit [num1+num2,num1+num2+num2])
    |otherwise = euler2 limit [num1+num2,num1+num2+num2]
euler2 limit [] = euler2 limit [1,2]

Which produced the following error: 产生了以下错误:

Occurs check: cannot construct the infinite type: a0 = [a0]
In the second argument of `(>)', namely `limit'
In the first argument of `(&&)', namely `(num2 > limit)'
In the expression: ((num2 > limit) && ((mod num1 2) == 0))

Now through some trial and error, I have realized that it is attempting to typecast num2 as a list, and this small change: 现在,通过一些反复试验,我意识到它正在尝试将num2作为列表进行类型转换,并且进行了一个小的更改:

euler2 limit (num1:num2:[]) | (num1 > limit) = 0

fixes the problem. 解决问题。 My question is why? 我的问题是为什么? What is going on and why was it refusing to cast num1 and num2 as Ints? 这是怎么回事,为什么它拒绝将num1num2为Ints?

The type of (:) is (:)的类型是

(:) :: a -> [a] -> [a]

If you have a pattern match 如果您有图案匹配

euler2 limit (num1:num2)

the names num1 and num2 are bound to the corresponding arguments of the constructor (:) (if the supplied argument is a nonempty list), thus num2 is a list whose elements have the type of num1 . 名称num1num2绑定到构造函数(:)的相应参数(如果提供的参数是非空列表),因此num2是其元素类型为num1的列表。

If you match on 如果您符合

(num1:num2:[])

that is implicitly parenthesized 隐含在括号中

(num1 : (num2 : []))

and now num2 : [] is matched with the list that is the second argument of the top-level (:) , and that match succeeds, binding num2 to the second list element, if the supplied argument is a list with exactly two elements. 现在, num2 : []与作为顶级(:)的第二个参数的列表匹配,并且如果提供的参数是一个包含两个元素的列表,则匹配成功,将num2绑定到第二个list元素。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM