Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/spring-mvc/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
当返回的对象不是字符串时,在Haskell中引发异常。_Haskell_Exception - Fatal编程技术网

当返回的对象不是字符串时,在Haskell中引发异常。

当返回的对象不是字符串时,在Haskell中引发异常。,haskell,exception,Haskell,Exception,所以我在用Haskell编写一个程序,它收到一个数字n,告诉它返回第n个素数,从2开始是第一个素数。程序的这一部分可以工作,但我不明白的是,当数字为0或更少时,如何让程序也抛出异常 pr :: Int -> Int pr n = (filter(\x -> (getter) == []) [2..]) !! (n-1) getter引用了我编写的另一种方法,即解决基本问题。它工作得很好 默认情况下,如果函数的公式与给定参数不匹配,则会出现运行时错误: fromJust :: May

所以我在用Haskell编写一个程序,它收到一个数字n,告诉它返回第n个素数,从2开始是第一个素数。程序的这一部分可以工作,但我不明白的是,当数字为0或更少时,如何让程序也抛出异常

pr :: Int -> Int
pr n = (filter(\x -> (getter) == []) [2..]) !! (n-1)

getter引用了我编写的另一种方法,即解决基本问题。它工作得很好

默认情况下,如果函数的公式与给定参数不匹配,则会出现运行时错误:

fromJust :: Maybe a -> a
fromJust (Just a) = a
-- No case for Nothing
-- fromJust Nothing throws error at runtime
然而,这不适用于数字。相反,警卫会做类似的事情:

assertOver0 :: Int -> ()
assertOver0 n | n > 0 = ()
-- No case for n <= 0
-- assertOver0 (-1) throws error at runtime
Haskell在中还有一个更复杂的异常机制,但这里可能不需要。一般来说,异常和部分函数都会被轻视(因为您只能在
IO
中处理它们),您应该努力使用单子,比如
可能
或者
或者

import Control.Monad
pr n = do guard $ n >= 0 -- guard True = Just (); guard False = Nothing (in this case)
          return $ filter (null . getter) [2..] !! n
pr 2 = Just 5
pr (-1) = Nothing
不过,所有这些都是不必要的<代码>(!!)
已出现负索引错误

ghci> "abc" !! -1
*** Exception: Prelude.!!: negative index
我们回到了起点:

pr n = filter (null . getter) [2..] !! n

还有一种方法将列表操作(包括
(!!)
)重新定义为一元操作,而不是部分操作。

默认情况下,如果函数的公式与给定参数不匹配,则会出现运行时错误:

fromJust :: Maybe a -> a
fromJust (Just a) = a
-- No case for Nothing
-- fromJust Nothing throws error at runtime
然而,这不适用于数字。相反,警卫会做类似的事情:

assertOver0 :: Int -> ()
assertOver0 n | n > 0 = ()
-- No case for n <= 0
-- assertOver0 (-1) throws error at runtime
Haskell在中还有一个更复杂的异常机制,但这里可能不需要。一般来说,异常和部分函数都会被轻视(因为您只能在
IO
中处理它们),您应该努力使用单子,比如
可能
或者
或者

import Control.Monad
pr n = do guard $ n >= 0 -- guard True = Just (); guard False = Nothing (in this case)
          return $ filter (null . getter) [2..] !! n
pr 2 = Just 5
pr (-1) = Nothing
不过,所有这些都是不必要的<代码>(!!)
已出现负索引错误

ghci> "abc" !! -1
*** Exception: Prelude.!!: negative index
我们回到了起点:

pr n = filter (null . getter) [2..] !! n

还有一种方法将列表操作(包括
(!!)
)重新定义为一元操作,而不是部分操作。

在Haskell中,基本上所有操作都只是一个库函数。因此,在线搜索引擎很容易找到它。这包括错误处理。所以你可以,或者,或者。这三种方法都存在,但只以不同的风格出现,专门针对特定的库,而和是
base
的一部分,因此也是“Haskell本身”的一部分

  • throw
    可用于生成正确类型的异常,如果您可能在程序本身的某个时刻想要捕获/分析错误,则它非常适合
  • error
    最有用的方法是在终端上生成(希望是)有用的诊断消息时使程序崩溃,这似乎就是您想要的
自GHC-8起,
错误的类型为†

error :: HasCallStack => String -> a
HasCallStack
是最近添加的,它允许程序告诉您代码中发生错误的位置。但这不会改变您使用函数的方式;在GHC的旧版本中,该类型只是

error :: String -> a
这意味着,您只需给出
error
一些错误消息,然后将其用作任何函数的“结果”,而不管该函数的结果类型是什么。就你而言

pr n | n >= 0     = ...
     | otherwise  = error "Table flip"
如果给此函数一个负数,则它不会给出任何实际结果,而是会通过消息
Table flip
使程序崩溃,并且在GHC>=8中,还会告诉您此错误发生在
pr

您可能还想知道在哪里调用了
pr
,以便实际调试问题。您可以自己使用GHC调用堆栈模拟进行以下操作:

import GHC.Stack

pr :: HasCallStack => Int -> Int
pr n | n >= 0     = ...
     | otherwise  = error "Table flip"
注意,我不需要以任何方式更改实现,我只是添加了
HasCallStack
约束


† 如果你往里看,你会看到一个相当可怕的签名

error :: forall (r :: RuntimeRep). forall (a :: TYPE r). HasCallStack => [Char] -> a

…不用担心,这些只是实现细节,提出了一些有意义的错误。事实上,Haskell语言并不那么自然地支持抛出错误。

在Haskell中,基本上一切都只是一个库函数。因此,在线搜索引擎很容易找到它。这包括错误处理。所以你可以,或者,或者。这三种方法都存在,但只以不同的风格出现,专门针对特定的库,而和是
base
的一部分,因此也是“Haskell本身”的一部分

  • throw
    可用于生成正确类型的异常,如果您可能在程序本身的某个时刻想要捕获/分析错误,则它非常适合
  • error
    最有用的方法是在终端上生成(希望是)有用的诊断消息时使程序崩溃,这似乎就是您想要的
自GHC-8起,
错误的类型为†

error :: HasCallStack => String -> a
HasCallStack
是最近添加的,它允许程序告诉您代码中发生错误的位置。但这不会改变您使用函数的方式;在GHC的旧版本中,该类型只是

error :: String -> a
这意味着,您只需给出
error
一些错误消息,然后将其用作任何函数的“结果”,而不管该函数的结果类型是什么。就你而言

pr n | n >= 0     = ...
     | otherwise  = error "Table flip"
如果给此函数一个负数,则它不会给出任何实际结果,而是会通过消息
Table flip
使程序崩溃,并且在GHC>=8中,还会告诉您此错误发生在
pr

您可能还想知道在哪里调用了
pr
,以便实际调试问题。您可以自己使用GHC调用堆栈模拟进行以下操作:

import GHC.Stack

pr :: HasCallStack => Int -> Int
pr n | n >= 0     = ...
     | otherwise  = error "Table flip"
注意,我不需要以任何方式更改实现,我只是添加了
HasCallStack
约束


† 如果你往里看,你会看到一个相当可怕的签名

error :: forall (r :: RuntimeRep). forall (a :: TYPE r). HasCallStack => [Char] -> a
…不用担心,这些只是实现细节,引发严重错误事实上并非如此