在Haskell中将Maybe Int转换为Int

Rog*_*ews 7 haskell

我正在处理以下代码,并希望在框字符串中找到数字的索引.所以我使用了findIndex,但它返回了Maybe Int值,而我只想要Int值.

我如何将Maybe Int转换为Int值,或者有什么方法可以从Maybe Int中提取Int.如果Maybe Int不存在,代码应该输出错误消息

box:: String
box = unlines $ ["0 | 1 | 2",
                 "---------",
                 "3 | 4 | 5",
                 "---------",
                 "6 | 7 | 8"]

moves = do
        putStrLn " Enter the number"
        number <- readLn :: IO Int
        print number
        findpostion number box

findposition number box = findIndex (==number) box
Run Code Online (Sandbox Code Playgroud)

Tik*_*vis 17

您可以在do语句中使用模式匹配轻松完成此操作:

case findposition number box of
  Just n  -> -- do whatever with n
  Nothing -> putStrLn "Invalid number!" -- you can handle the error however you want.
Run Code Online (Sandbox Code Playgroud)

一个很好的选择是创建一个单独的IO动作来获取数字:

getNumber = do putStrLn "Enter the number:"
               number <- readLn
               case findposition number box of
                 Just n  -> -- Do whatever
                 Nothing -> putStrLn "Please try again." >> getNumber
Run Code Online (Sandbox Code Playgroud)

这样,如果用户输入了无效的号码,它就会再次询问.

此外,正如现在所写,您的代码将无法正常工作.您应该有其他方式将数字存储box为实际数字; 现在,他们在弦乐队.


lef*_*out 11

显然,一般情况下不可能:当搜索没有成功时,没有规范的整数返回值,所以你得到一个Nothing没有任何这样的值.

如果你真的不关心这种Nothing情况(例如因为你总会确保有一个这样的元素)你可以使用该fromJust功能Data.Maybe,你也可以自己快速实现:

findposition number = (\(Just i)->i) . findIndex (==number)
Run Code Online (Sandbox Code Playgroud)

然而,这不是真的值得推荐,因为你需要确保这不会中断,而且这样做是正确的模式匹配的方法要容易得多.

  • 如果*是*你正在使用的上下文的"规范整数",你可以使用`fromMaybe canonicalInt maybeVal`,其中`canonicalInt :: Int`和`maybeVal :: Maybe Int`.参见[Data.Maybe docs](http://hackage.haskell.org/packages/archive/base/latest/doc/html/Data-Maybe.html#v:fromMaybe) (4认同)