您好,我正在尝试完成CIS194 Spring13,当我在我的一个函数上收到错误消息*** Exception: Prelude.read: no parse时。函数所在的文件名为LogAnalysis.hs,函数为parseMessage,但该文件也是从Log.hs导入的。为什么我会收到这个错误消息,我该如何修复它?
下面是我的代码:https://github.com/Adam-Morris/CIS194/tree/master/Homework-2
发布于 2016-09-10 20:39:02
read是一个read :: Read a => String -> a类型的函数。这意味着read接受String作为输入,并返回某个类型a的值,前提是a实现了Read类型类。read必须知道要返回的特定类型,并且可以通过以下两种方式之一知道:要么显式地将类型赋予它(例如read "123" :: Int或read "True" :: Bool),要么从上下文中推断出类型。在您的例子中,read推断它必须返回一个Int,因为LogMessage期望Int作为它的第二个参数。因此,在本例中,表达式read [y]的意思是:获取Char y,将其转换为单元素字符串,然后尝试通过解析将其转换为Int。现在,如果y碰巧包含一个不是十进制数字的字符,它将失败(通过抛出异常),因为它不知道如何将其转换为整数。
现在你如何处理这个问题呢?在调用read之前,必须检查它的输入是否正确。例如,您可以(使用appropriate function)检查y是否为数字:
parseMessage (x:y:z)
| x == 'I' && isDigit y = LogMessage Info (read [y]) (unwords [z])
...或者,您可以使用类似于read的Text.Read中的readMaybe,但如果失败,它不会抛出异常,而是返回一个nothing值:
parseMessage (x:y:z)
| x == 'I', Just n <- readMaybe [y] = LogMessage Info n (unwords [z])发布于 2016-09-10 21:09:29
问题出在您的输入消息格式。将一行作为字符串读取,然后匹配字符串中的字符(因为字符串是[Char]的类型别名)。在sample.log中,第一行(I 6 Completed armadillo processing)将作为字符串传递给parseMessage,参数将采用以下值:
x = 'I'
y = ' ' --single white space character
z = "6 Completed armadillo processing"
read获取空白字符并抛出*** Exception: Prelude.read: no parse
为了获取这些值,您可以执行以下操作:
parseMessage :: String -> LogMessage
parseMessage msg =
case words msg of
"I":y:z -> LogMessage Info (read y :: TimeStamp) (unwords z)
"W":y:z -> undefined
"E":y:z -> undefined
_ -> undefined这样就可以很容易地提取前两个有效单词(在本例中为MessageType和TimeStamp )。
https://stackoverflow.com/questions/39426111
复制相似问题