2

我正在尝试从文件中获取一些数据,然后对其进行解析并将其作为参数传递给另一个函数。

data LogLine = LogLine {
  name      :: String
, args1     :: String
, args2     :: String
, constant  :: String 
} deriving (Ord, Show, Eq)

main = do 
file <- readFile "foo"
let result = (parse final "Input" file) --Parses the file into the LogLine datatype
let firstargs = getFirstArgs result --Get the first argument out of the datatype
let secondargs = getSecondArgs result --Get the second argument out of the datatype
let constant = getConstant result --Get the constant out of the datatype
createGraph firstargs secondargs constant --THIS IS THE PROBLEM

问题是,每当我尝试读入一个文件时,它就会变成一个(IO 字符串),无论我做什么,我都必须携带 IO。该createGraph函数被声明为

createGraph :: String -> String -> String -> Argument

但是每当我尝试执行最后一条语句时,它都会抱怨:

Couldn't match expected type `IO a0' with actual type `Argument'
In the return type of a call of `createGraph'

我不允许更改createGraph函数的返回类型,因为它是我需要向其提供参数的大型框架的一部分。有哪些处理方法?

4

2 回答 2

2

你为什么想这么做?

让你的价值进入 IO monad 的唯一方法是使用 return。您可以将对 createGraph 的调用包装到另一个函数中,例如

returnGraph a b c = return $ createGraph a b c

或者只是使用另一个 let 绑定并在需要时使用您的值。我不知道你想在那里做什么。请给我们更多细节,比如你想对返回值做什么。

- 根据我从您的评论中了解到的情况,您只需要返回参数,因此您唯一要做的就是返回 $ createGraph firstargs secondargs 常量并将函数从 main 重命名为其他内容,因为 main 必须具有类型 IO ()。

于 2012-10-09T00:22:05.560 回答
1

问题是,每当我尝试读入一个文件时,它就会变成一个(IO 字符串),无论我做什么,我都必须携带 IO。

我不认为这是真正的问题。问题是 main 的返回类型为 IO() ,这是执行的最后一行的结果。在这种情况下,这意味着createGraph导致参数的调用。这就是你得到类型错误的原因,它与从文件中读取的 IO 字符串无关。

一种解决方案是简单地返回createGraphmain 末尾的结果:

return $ createGraph firstargs secondargs constant
于 2012-10-09T00:35:38.083 回答