我正在尝试用SBV解决算术问题。
例如
solution :: SymbolicT IO ()
solution = do
[x, y] <- sFloats ["x", "y"]
constrain $ x + y .<= 2
Main> s1 = sat solution
Main> s2 = isSatisfiable solution
Main> s1
Satisfiable. Model:
x = -1.2030502e-17 :: Float
z = -2.2888208e-37 :: Float
Main> :t s1
s1 :: IO SatResult
Main> s2
True
Main> :t s2
s2 :: IO Bool
虽然我可以做有用的事情,但我更容易使用纯值(SatResult 或 Bool)而不是 IO monad。
根据文档
sat :: Provable a => a -> IO SatResult
constrain :: SolverContext m => SBool -> m ()
sFloats :: [String] -> Symbolic [SFloat]
type Symbolic = SymbolicT IO
鉴于我使用的函数类型,我理解为什么我总是使用 IO monad。
但是查看函数的通用版本,例如 sFloats。
sFloats :: MonadSymbolic m => [String] -> m [SFloat]
根据函数的类型,我可以使用与 IO 不同的 monad。这给了我希望,我们将获得一个更有用的 monad,例如 Identity monad。
不幸的是,查看示例总是可以解决 IO monad 中的问题,所以我找不到任何适合我的示例。此外,我没有太多使用 monad 的经验。
最后我的问题是:
在用 SBV 解决此类问题时,有什么方法可以避免 IO monad?
提前致谢