
Thanks for the responses! If Haskell report says so, it's fine to leave it
as it is - I do have it in mind that Read isn't supposed to be used this
way.
To be fair, "(x,s) is an element of (readsPrec d (showsPrec d x s))" is
indeed a stronger property than it needs to be.
But still, it is worth taking a note as concerns when using `readS_to_P
reads`.
Cheers,
Javran
On Thu, Mar 28, 2019 at 4:09 AM Brent Yorgey
The 2010 Haskell Report specifies that
(x,"") is an element of (readsPrec d (showsPrec d x ""))
Notice it does NOT say that
(x,s) is an element of (readsPrec d (showsPrec d x s))
which would be false, as your example shows by setting x = 123 and s = ".456".
read really isn't meant to be a general-purpose parser; it only works on sequences of lexical tokens. As Ömer points out, reads @Int and reads @Double both depend on 'lex', and there is no way for 'lex' to know what kind of thing reads is ultimately trying to parse. If you changed lex so that lex "123.456aaa" returns [("123", ".456aaa")] then reads @Double would break. I suppose you could try to change lex so that lex "123.456aaa" returns [("123", ".456aaa"), ("123.456", "aaa")] but this seems like a lot of work for little benefit. If you are running into this kind of issue with Read instances, it strongly suggests to me that you should be using a proper parsing library rather than Read.
-Brent
On Thu, Mar 28, 2019 at 5:08 AM Ömer Sinan Ağacan
wrote: Hi,
I'm not sure if this is a bug, but I think the problem is in the lexer, not in the part that that tries to convert a single token to a value of the given type. Example:
λ:1> lex "123" [("123","")]
λ:2> lex "123.aaa" [("123",".aaa")]
λ:3> lex "123.456aaa" [("123.456","aaa")]
So in "123.aaa" you actually convert "123" to an Int, but in "123.456aaa" you try to convert "123.456" to an Int, which fails.
Not sure how hard would it be to improve this (while keeping things standard-compliant) or whether it's worth the effort.
Ömer
Javran Cheng
, 27 Mar 2019 Çar, 10:17 tarihinde şunu yazdı: Hi Cafe,
Not sure if there are existing discussions, but I recently run into a
problem with Read instance of Int:
Prelude> :set -XTypeApplications Prelude> reads @Int "123." [(123,".")] Prelude> reads @Int "123.aaa" [(123,".aaa")] Prelude> reads @Int "123.456aaa" [] -- I expected this to be [(123,".456aaa")] Prelude> reads @Double "123.234aaa" [(123.234,"aaa")]
Further investigation shows that [realNumber](
I think what happened is that when the leading parser input can be
http://hackage.haskell.org/package/base/docs/src/GHC.Read.html#readNumber) is used for Read instance of Int. parsed as a floating number, it will do so and commit to that decision, making backtracking impossible.
I do understand that Read just need to be able to parse whatever Show
When I'm using Text.ParserCombinators.ReadP, I really appreciates it
can produce and is not designed to deal with raw inputs, but this is still a surprising behavior to me. that I can use `readP_to_S read` to parse simple values (integers and floating points in particular),
but it bothers me that parsing Int from "123.aaa" is fine but "123.1aa" will fail simply because the not-yet-consumed part of input is different.
Javran _______________________________________________ Haskell-Cafe mailing list To (un)subscribe, modify options or view archives go to: http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe Only members subscribed via the mailman list are allowed to post.
Haskell-Cafe mailing list To (un)subscribe, modify options or view archives go to: http://mail.haskell.org/cgi-bin/mailman/listinfo/haskell-cafe Only members subscribed via the mailman list are allowed to post.
-- Javran (Fang) Cheng