“多重声明”模式与通配符匹配时出错

发布于 2024-10-14 22:40:25 字数 1081 浏览 5 评论 0原文

出于学习目的,我尝试编写自己的 zipWith 函数实现。但是,我在使用 _ 的边缘情况下遇到了模式匹配问题。首先我将描述好的情况,然后描述坏的情况。希望有人能够解释为什么他们的行为不同。谢谢

如果我按如下方式编写 zipWith 函数,它就可以工作(注意第 2 行和第 3 行中与空列表匹配的边缘情况的顺序):-

zipWith' :: (a -> b -> c) -> [a] -> [b] -> [c]
zipwith' _ [] _ = []
zipWith' _ _ [] = []
zipWith' f (x:xs) (y:ys) = f x y : zipWith' f xs ys

在 GHCI 中编译:-

ghci> :l ZipWith.hs 
[1 of 1] Compiling Main             ( ZipWith.hs, interpreted )

好的,上面的没问题,但是如果我交换 GHCI 周围边缘情况的模式匹配,则会在第 2 行和第 4 行抛出“多重声明”错误。

zipWith' :: (a -> b -> c) -> [a] -> [b] -> [c]
zipWith' _ _ [] = []
zipwith' _ [] _ = []
zipWith' f (x:xs) (y:ys) = f x y : zipWith' f xs ys

在 GHCI 中编译:-

ZipWith.hs:4:0:
    Multiple declarations of `Main.zipWith''
    Declared at: ZipWith.hs:2:0
                 ZipWith.hs:4:0
Failed, modules loaded: none.

我被难住了......

  1. 看看第 2 行和第 4 行上的模式,它们似乎相互排斥,但我显然在这里遗漏了一些基本的东西,
  2. 为什么切换第 2 行和第 3 行的模式会导致编译错误消失。

For learning purposes I am trying to write my own implementation of the zipWith function. However, I am hitting an issue with pattern matching on edge cases with _. First I will describe the good case, then the bad case. Hopefully someone will be able to explain why they behave differently. Thanks

If I write the zipWith function as follows, it works (Note the order of the edge cases matching empty list on lines 2 & 3):-

zipWith' :: (a -> b -> c) -> [a] -> [b] -> [c]
zipwith' _ [] _ = []
zipWith' _ _ [] = []
zipWith' f (x:xs) (y:ys) = f x y : zipWith' f xs ys

Compiling in GHCI:-

ghci> :l ZipWith.hs 
[1 of 1] Compiling Main             ( ZipWith.hs, interpreted )

Ok, the above is fine, yet if I swap the pattern matching for the edge cases around GHCI throws 'Multiple declarations of' error for lines 2 and 4.

zipWith' :: (a -> b -> c) -> [a] -> [b] -> [c]
zipWith' _ _ [] = []
zipwith' _ [] _ = []
zipWith' f (x:xs) (y:ys) = f x y : zipWith' f xs ys

Compiling in GHCI:-

ZipWith.hs:4:0:
    Multiple declarations of `Main.zipWith''
    Declared at: ZipWith.hs:2:0
                 ZipWith.hs:4:0
Failed, modules loaded: none.

I'm stumped...

  1. Looking at the patterns on lines 2 and 4 they seem mutually exclusive but i'm obviously missing something fundamental here
  2. Why would switching the patterns on lines 2 and 3 cause the compilation error to go away.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

浅浅 2024-10-21 22:40:25

错误消息并不是抱怨模式重叠(在两个空列表的情况下,您的模式确实重叠,但这既不是问题,也不是问题),而是 zipWith 函数的多个定义。

原因是在第二种情况下,您有一个 zipWith 定义,后跟一个不相关的 zipwith 定义(请注意小写的 w ),后跟一个新的、相互冲突的 zipWith 定义。换句话说,这是一个简单的错字。 (我确实花了一段时间才看到——这是一个偷偷摸摸的打字错误)

The error message isn't complaining about overlapping patterns (your patterns do overlap in the case of two empty lists, but that's neither the problem, nor a problem), but multiple definitions of the zipWith function.

The reason for that is that in your second case you have one definition of zipWith followed by an unrelated definition of zipwith (note the lower case w), followed by a new, conflicting definition of zipWith. In other words it's a simple typo. (Did take me a while to see though - quite a sneaky typo)

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文