模式匹配的严格性与解构

Strictness of pattern matching vs. deconstructing

我正在尝试根据 foldr 定义原始递归,如 A tutorial on the universality and expressiveness on fold 第 4.1 章中所述。

这是第一次尝试

simpleRecursive f v xs = fst $ foldr g (v,[]) xs
  where 
    g x (acc, xs) = (f x xs acc,x:xs)

但是,上面的定义不会停止 head $ simpleRecursive (\x xs acc -> x:xs) [] [1..]

下面是halt

的定义
simpleRecursive f v xs = fst $ foldr g (v,[]) xs
  where 
    g x r = let (acc,xs) = r
            in (f x xs acc,x:xs)

给定几乎相似的定义但不同的结果,为什么会不同?它与 Haskell 模式匹配的方式有关吗?

这两个函数的关键区别在于

g x r = let (acc, xs) = r
        in (f x xs acc, x:xs)

元组构造函数中的模式匹配是无可辩驳的,而在

g x (acc, xs) = (f x xs acc, x:xs)

不是。也就是说,g的第一个定义等同于

g x ~(acc, xs) = (f x xs acc, x:xs)