我正在尝试编写一个简单的 Haskell 函数来区分空列表和非空列表。这是我的代码:
doneVsItems :: [Int] -> IO ()
doneVsItems [] = putStrLn "Done"
doneVsItems (p:ps) = putStrLn "Items"
但是,当我在启用 -Werror=incomplete-patterns 的情况下编译代码时,出现以下错误:
error: [GHC-62161] [-Wincomplete-patterns (in -Wextra), Werror=incomplete-patterns]
Pattern match(es) are non-exhaustive
In an equation for `doneVsItems':
Patterns of type `[Int]' not matched: []
|
21 | doneVsItems [] = putStrLn "Done"
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^...
我在空列表 ([]) 和非空列表 ((p:ps)) 上显式进行模式匹配,所以我不明白为什么 GHC 说模式匹配是非详尽的。我在这里缺少什么?
附加信息:
• I’m using ghc-9.8.2 with the following options enabled:
-Werror=compat-unqualified-imports
-Werror=deprecations
-Werror=dodgy-imports
-Werror=incomplete-patterns
-Werror=incomplete-record-updates
-Werror=incomplete-uni-patterns
-Werror=name-shadowing
-Werror=partial-type-signatures
-Werror=prepositive-qualified-module
-Werror=type-defaults
-Werror=typed-holes
-fprint-explicit-kinds
-Wno-redundant-constraints
-fenable-th-splice-warnings.
任何关于为什么 GHC 将其标记为非详尽模式匹配的帮助将不胜感激!
这确实是一个非常奇怪的情况,尤其是它抱怨缺少
[]
模式并指向 []
模式。但我有一个猜测:这个定义是在 where
子句中做出的,但只是部分定义。例如这段代码:
foo = () where
doneVsItems [] = ()
doneVsItems (p:ps) = ()
产生这些警告:
test.hs:2:2: warning: [GHC-62161] [-Wincomplete-patterns]
Pattern match(es) are non-exhaustive
In an equation for ‘doneVsItems’:
Patterns of type ‘[a]’ not matched: (_:_)
|
2 | doneVsItems [] = ()
| ^^^^^^^^^^^^^^^^^^^
test.hs:3:1: warning: [GHC-62161] [-Wincomplete-patterns]
Pattern match(es) are non-exhaustive
In an equation for ‘doneVsItems’:
Patterns of type ‘[a]’ not matched: []
|
3 | doneVsItems (p:ps) = ()
| ^^^^^^^^^^^^^^^^^^^^^^^
也许您不小心复制并粘贴了一个警告的一部分和另一个警告的一部分???
如果您的编辑器的制表符未设置为 8 个空格,则两个子句的缩进可能看起来相同,但会被视为不同,因此,如果肉眼看起来没问题,需要检查的一件事是两个子句中的制表符是否相同线条一致。