gpt4 book ai didi

haskell - 模式 x * y 中的解析错误(case 语句)

转载 作者:行者123 更新时间:2023-12-03 08:02:42 25 4
gpt4 key购买 nike

我有这个代码:

module BalancedTwoDozenMultDrill where
import BalancedTwoDozenLib
myRandoms :: Int -> IO [Int]
myRandoms n = let x = 24^n `div` 2 in randomRs (-x,x) <$> getStdGen
drill :: [Int] -> IO ()
drill (x:y:rs) = do
putStr $ showInt x ++ " × " ++ showInt y ++ " = "
a <- getLine
case a of
"" -> return ()
showInt (x * y) -> do -- <= here
putStrLn "Correct"
drill rs
_ -> do
putStrLn $ "Wrong; " ++ showInt (x * y)
drill rs
main :: IO [Int]
main = drill =<< myRandoms =<< readLn

并得到错误:
BalancedTwoDozenMultDrill.hs:11:18: Parse error in pattern: x * y

但是,将部分 case 语句替换为:
    -- ...stuff
let i = showInt (x * y)
case a of
"" -> return ()
i -> do
-- stuff...

使其解析(它会出现“不在范围内”错误,我可以修复)。我看到第一个片段错误的唯一原因是正在执行功能应用程序。我不能在case语句中使用普通函数应用程序作为替代方案,这是真的吗?

最佳答案

当你在 case 语句中有一个模式时,它必须遵循与函数参数的模式匹配相同的规则。只有文字、构造函数和通配符 _可以匹配上,而不是功能应用。相反,你可以做一些更像

a <- getLine
let xyStr = showInt (x * y) -- Avoid recomputation with a let binding
when (not $ null a) $ do
if a == xyStr
then do
putStrLn "Correct"
drill rs
else do
putStrLn $ "Wrong; " ++ xyStr
drill rs

您需要导入 when来自 Control.Monad , 尽管。

在 case 语句中必须遵循与函数定义中的模式匹配相同的规则的原因是因为编译器实际上转换了类似
head :: [a] -> a
head (x:xs) = x
head _ = error "Prelude.head: empty list"

进入
head :: [a] -> a
head list = case list of
(x:xs) -> x
_ -> error "Prelude.head: empty list"

我们拥有前一个版本的唯一原因是方便,它通常使代码看起来更漂亮。

This链接应该能够为您提供更全面的解释,说明什么是有效的模式匹配结构,什么不是有效的模式匹配结构。

您遇到的另一个问题是尝试替换 showInt (x * y)i在哪里 let i = showInt (x * y) .执行此操作时,首先绑定(bind)值 showInt (x * y)i ,然后在你的案例陈述中你有模式
"" -> ...
i -> ...
_ -> ...

所以现在你的模式是 i ,它会在 "" 之后表现得像一个包罗万象的模式.这将重新绑定(bind)名称 i对于该案例陈述的范围。

要记住的一个好规则是,您不能对运行时获得的值进行模式匹配,您必须检查相等或其他比较操作。

关于haskell - 模式 x * y 中的解析错误(case 语句),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25059430/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com