Print values stored in an "Either" in the main method

I have a module that looks like this runEval :: (Show a) => Env -> Eval a -> Either String a runEval = ... data Value = IntVal Integer main :: IO () main = do let env = Map.fromList [("x",IntVal 3)] result <- runEval env (eval (Plus (Var "x") (Lit 2))) case result of Left err -> putStrLn "Error: "++err Right (IntVal i) -> print i when I call runEval from ghci I get back a result just fine let env = Map.fromList [("x",IntVal 3)] runEval env (eval (Plus (Var "x") (Lit 2))) This outputs "Right (IntVal 5)" as I would expect. But when I try and compile my main method I get the following error. Couldn't match expected type `Value' with actual type `Either t1 Value' In the pattern: Right (IntVal i) In a case alternative: Right (IntVal i) -> print i In a stmt of a 'do' block: case result of { Left err -> print err Right (IntVal i) -> print i } I also tried using (putStrLn . either show show) result, but this gave me the following error. Couldn't match expected type `Either a0 b0' with actual type `Value' In the first argument of `putStrLn . either show show', namely `result' In a stmt of a 'do' block: (putStrLn . either show show) result In the expression: do { let env = Map.fromList ...; result <- runEval3 env (eval3 (Plus (Var "x") (Lit 2))); (putStrLn . either show show) result } Why is it when I try and pattern match on Either String Value it says result is of type "Value", but when I try and use either it says result is of type "Either String Value"? Matt P.

Because you didn't put all your code, I'm not sure if this is correct, but
my best guess is that you expect runEval to return Either String a, but the
way you are using it I suspect you actually want its type to be IO (Either
String a).
Alternatively change
result <- runEval env (eval (Plus (Var "x") (Lit 2)))
to
let result = runEval env (eval (Plus (Var "x") (Lit 2)))
On Thu, Feb 20, 2014 at 7:19 PM, Mathew Phillips
I have a module that looks like this
runEval :: (Show a) => Env -> Eval a -> Either String a runEval = ...
data Value = IntVal Integer
main :: IO () main = do let env = Map.fromList [("x",IntVal 3)] result <- runEval env (eval (Plus (Var "x") (Lit 2))) case result of Left err -> putStrLn "Error: "++err Right (IntVal i) -> print i
when I call runEval from ghci I get back a result just fine
let env = Map.fromList [("x",IntVal 3)] runEval env (eval (Plus (Var "x") (Lit 2)))
This outputs "Right (IntVal 5)" as I would expect. But when I try and compile my main method I get the following error.
Couldn't match expected type `Value' with actual type `Either t1 Value' In the pattern: Right (IntVal i) In a case alternative: Right (IntVal i) -> print i In a stmt of a 'do' block: case result of { Left err -> print err Right (IntVal i) -> print i }
I also tried using (putStrLn . either show show) result, but this gave me the following error.
Couldn't match expected type `Either a0 b0' with actual type `Value' In the first argument of `putStrLn . either show show', namely `result' In a stmt of a 'do' block: (putStrLn . either show show) result In the expression: do { let env = Map.fromList ...; result <- runEval3 env (eval3 (Plus (Var "x") (Lit 2))); (putStrLn . either show show) result }
Why is it when I try and pattern match on Either String Value it says result is of type "Value", but when I try and use either it says result is of type "Either String Value"?
Matt P.
_______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners

Ok now I'm even more confused! That works, but I thought that "let" was for
when the value inside the do block was pure, and the <- notation when it's
inside another monad?
On Thu, Feb 20, 2014 at 7:01 PM, David McBride
Because you didn't put all your code, I'm not sure if this is correct, but my best guess is that you expect runEval to return Either String a, but the way you are using it I suspect you actually want its type to be IO (Either String a).
Alternatively change
result <- runEval env (eval (Plus (Var "x") (Lit 2)))
to
let result = runEval env (eval (Plus (Var "x") (Lit 2)))
On Thu, Feb 20, 2014 at 7:19 PM, Mathew Phillips < mathewrphillips@gmail.com> wrote:
I have a module that looks like this
runEval :: (Show a) => Env -> Eval a -> Either String a runEval = ...
data Value = IntVal Integer
main :: IO () main = do let env = Map.fromList [("x",IntVal 3)] result <- runEval env (eval (Plus (Var "x") (Lit 2))) case result of Left err -> putStrLn "Error: "++err Right (IntVal i) -> print i
when I call runEval from ghci I get back a result just fine
let env = Map.fromList [("x",IntVal 3)] runEval env (eval (Plus (Var "x") (Lit 2)))
This outputs "Right (IntVal 5)" as I would expect. But when I try and compile my main method I get the following error.
Couldn't match expected type `Value' with actual type `Either t1 Value' In the pattern: Right (IntVal i) In a case alternative: Right (IntVal i) -> print i In a stmt of a 'do' block: case result of { Left err -> print err Right (IntVal i) -> print i }
I also tried using (putStrLn . either show show) result, but this gave me the following error.
Couldn't match expected type `Either a0 b0' with actual type `Value' In the first argument of `putStrLn . either show show', namely `result' In a stmt of a 'do' block: (putStrLn . either show show) result In the expression: do { let env = Map.fromList ...; result <- runEval3 env (eval3 (Plus (Var "x") (Lit 2))); (putStrLn . either show show) result }
Why is it when I try and pattern match on Either String Value it says result is of type "Value", but when I try and use either it says result is of type "Either String Value"?
Matt P.
_______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners
_______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners

On Thu, Feb 20, 2014 at 8:05 PM, Mathew Phillips
Ok now I'm even more confused! That works, but I thought that "let" was for when the value inside the do block was pure, and the <- notation when it's inside another monad?
Are you referring to the fact that Either has a Monad instance? Because you're not *using* it monadically, but purely, so its Monad instance is not relevant. Likewise lists have a Monad instance, but most of the time you don't use it, you treat them as pure values. (You also can't mix monads; if you're using <- in a do block in IO, it must be working with a value in IO, not merely one in some monad. This is clearer when you learn how do blocks desugar into functions.) -- brandon s allbery kf8nh sine nomine associates allbery.b@gmail.com ballbery@sinenomine.net unix, openafs, kerberos, infrastructure, xmonad http://sinenomine.net

Actually your comment in parenthesis is what made it click. If i do "result
<- return $ runEval ..." it works too. The fact that the first error was
complaining that it expected something of type IO should have tipped me
off.
Thank you,
Matt P.
On Thu, Feb 20, 2014 at 7:10 PM, Brandon Allbery
On Thu, Feb 20, 2014 at 8:05 PM, Mathew Phillips < mathewrphillips@gmail.com> wrote:
Ok now I'm even more confused! That works, but I thought that "let" was for when the value inside the do block was pure, and the <- notation when it's inside another monad?
Are you referring to the fact that Either has a Monad instance? Because you're not *using* it monadically, but purely, so its Monad instance is not relevant. Likewise lists have a Monad instance, but most of the time you don't use it, you treat them as pure values.
(You also can't mix monads; if you're using <- in a do block in IO, it must be working with a value in IO, not merely one in some monad. This is clearer when you learn how do blocks desugar into functions.)
-- brandon s allbery kf8nh sine nomine associates allbery.b@gmail.com ballbery@sinenomine.net unix, openafs, kerberos, infrastructure, xmonad http://sinenomine.net
_______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners

On Thu, Feb 20, 2014 at 8:16 PM, Mathew Phillips
Actually your comment in parenthesis is what made it click. If i do "result <- return $ runEval ..." it works too. The fact that the first error was complaining that it expected something of type IO should have tipped me off.
Note also that, while using <- that way "should" have the same effect as using let, it forces the value to be sequenced with I/O actions, which you may not want. It may disable optimizations, for one thing, and changes laziness since it is now constrained by sequencing with I/O when I/O isn't actually involved with it. -- brandon s allbery kf8nh sine nomine associates allbery.b@gmail.com ballbery@sinenomine.net unix, openafs, kerberos, infrastructure, xmonad http://sinenomine.net
participants (3)
-
Brandon Allbery
-
David McBride
-
Mathew Phillips