Why will `read “1” :: Maybe Int` type check?

  • A+

I wonder why read "1" :: Maybe Int will type check and throw an exception in runtime.

Is it possible that read can ever return a Maybe a? That is what Text.Read.readMaybe is supposed to do.

Prelude> read "1" :: Maybe Int *** Exception: Prelude.read: no parse 


In short: you parse the textual representation of the Maybe a type, not a as a non-total function where Nothing is used to specify a parse failure.

Well read is usually the opposite of show. It will thus parse a representation of an object, that is frequently how you would write the object as a cascade of data constructors into an object.

Now Maybe a is a type of the Show family, given the elements it wraps are an instance of Show as well, something like:

instance Show a => Show (Maybe a) where     show Nothing = "Nothing"     show (Just x) = "Just "++ show x 

(In reality it is a bit more complex, since it will also introduce brackets in case you wrap a Just 1 in a Just for example).

So the opposite can be parsed as well. For example:

Prelude> read "Nothing" :: Maybe Int Nothing Prelude> read "Just 5" :: Maybe Int Just 5

So a Maybe a as a type of read is not meant for a "non-total" function, but to parse the textual representation of a Maybe a type.

So it parses strings with a prefix "Nothing" and "Just" (and also can parse some such "expressions" with brackets).


:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen: