reading and writing Data.Ratio.Rational

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
9 messages Options
Reply | Threaded
Open this post in threaded view
|

reading and writing Data.Ratio.Rational

Olaf Klinke
Dear cafe,

when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.

So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?

Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.

For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.

Any pointers are appreciated.
Thanks,
Olaf

[1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

ALeX Kazik
Hi,

> So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?

You can only parse "7%10".

ALeX.
_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

Patrick Chilton
In reply to this post by Olaf Klinke
Prelude> import Numeric
Prelude Numeric> fst $ head $ readFloat "0.1234" :: Rational
617 % 5000

On Fri, Feb 24, 2017 at 1:17 PM, Olaf Klinke <[hidden email]> wrote:
Dear cafe,

when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.

So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?

Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.

For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.

Any pointers are appreciated.
Thanks,
Olaf

[1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

Olaf Klinke
Ah, thanks! That is something to build on.

Olaf

> Am 24.02.2017 um 15:35 schrieb Patrick Chilton <[hidden email]>:
>
> Prelude> import Numeric
> Prelude Numeric> fst $ head $ readFloat "0.1234" :: Rational
> 617 % 5000
>
> On Fri, Feb 24, 2017 at 1:17 PM, Olaf Klinke <[hidden email]> wrote:
> Dear cafe,
>
> when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.
>
> So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?
>
> Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.
>
> For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.
>
> Any pointers are appreciated.
> Thanks,
> Olaf
>
> [1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
> _______________________________________________
> 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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

David Feuer
I think your best bet is probably to get your hands dirty and parse it yourself: first grab an integer, then optionally a decimal point, etc.

On Mar 6, 2017 3:43 PM, "Olaf Klinke" <[hidden email]> wrote:
Ah, thanks! That is something to build on.

Olaf
> Am 24.02.2017 um 15:35 schrieb Patrick Chilton <[hidden email]>:
>
> Prelude> import Numeric
> Prelude Numeric> fst $ head $ readFloat "0.1234" :: Rational
> 617 % 5000
>
> On Fri, Feb 24, 2017 at 1:17 PM, Olaf Klinke <[hidden email]> wrote:
> Dear cafe,
>
> when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.
>
> So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?
>
> Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.
>
> For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.
>
> Any pointers are appreciated.
> Thanks,
> Olaf
>
> [1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
> _______________________________________________
> 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.

_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

amindfv
There was a discussion recently on the list (started by me) about new versions of base parsing decimals as Rational. I think at this point someone just needs to roll their sleeves up and do it. I may be the one who ends up doing it, but don't have the bandwidth right now.

Tom


El 6 mar 2017, a las 14:46, David Feuer <[hidden email]> escribió:

I think your best bet is probably to get your hands dirty and parse it yourself: first grab an integer, then optionally a decimal point, etc.

On Mar 6, 2017 3:43 PM, "Olaf Klinke" <[hidden email]> wrote:
Ah, thanks! That is something to build on.

Olaf
> Am 24.02.2017 um 15:35 schrieb Patrick Chilton <[hidden email]>:
>
> Prelude> import Numeric
> Prelude Numeric> fst $ head $ readFloat "0.1234" :: Rational
> 617 % 5000
>
> On Fri, Feb 24, 2017 at 1:17 PM, Olaf Klinke <[hidden email]> wrote:
> Dear cafe,
>
> when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.
>
> So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?
>
> Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.
>
> For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.
>
> Any pointers are appreciated.
> Thanks,
> Olaf
>
> [1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
> _______________________________________________
> 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.
_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

Olaf Klinke
In reply to this post by David Feuer
Before asking on this list, I wrote my own version which did just what David suggested: Parse the integer before the decimal point, parse the part behind the decimal point and divide the latter by 10^length, then sum both parts. This function has type

Fractional t => String -> t

I thought that this was maybe very inefficient and therefore looked for prior art. If someone feels it is worth adding to some package, I'm happy to provide the code.

Olaf


> Am 06.03.2017 um 21:46 schrieb David Feuer <[hidden email]>:
>
> I think your best bet is probably to get your hands dirty and parse it yourself: first grab an integer, then optionally a decimal point, etc.
>
> On Mar 6, 2017 3:43 PM, "Olaf Klinke" <[hidden email]> wrote:
> Ah, thanks! That is something to build on.
>
> Olaf
> > Am 24.02.2017 um 15:35 schrieb Patrick Chilton <[hidden email]>:
> >
> > Prelude> import Numeric
> > Prelude Numeric> fst $ head $ readFloat "0.1234" :: Rational
> > 617 % 5000
> >
> > On Fri, Feb 24, 2017 at 1:17 PM, Olaf Klinke <[hidden email]> wrote:
> > Dear cafe,
> >
> > when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.
> >
> > So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?
> >
> > Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.
> >
> > For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.
> >
> > Any pointers are appreciated.
> > Thanks,
> > Olaf
> >
> > [1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
> > _______________________________________________
> > 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.

_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

Mike Ledger
I can never seem to remember to reply-all ...

On Wed, Mar 8, 2017 at 3:24 PM, Mike Ledger <[hidden email]> wrote:
There is also the exact-real and numbers packages which provide exact reals with their respective CReal types.

On Wed, Mar 8, 2017 at 6:22 AM, Olaf Klinke <[hidden email]> wrote:
Before asking on this list, I wrote my own version which did just what David suggested: Parse the integer before the decimal point, parse the part behind the decimal point and divide the latter by 10^length, then sum both parts. This function has type

Fractional t => String -> t

I thought that this was maybe very inefficient and therefore looked for prior art. If someone feels it is worth adding to some package, I'm happy to provide the code.

Olaf


> Am 06.03.2017 um 21:46 schrieb David Feuer <[hidden email]>:
>
> I think your best bet is probably to get your hands dirty and parse it yourself: first grab an integer, then optionally a decimal point, etc.
>
> On Mar 6, 2017 3:43 PM, "Olaf Klinke" <[hidden email]> wrote:
> Ah, thanks! That is something to build on.
>
> Olaf
> > Am 24.02.2017 um 15:35 schrieb Patrick Chilton <[hidden email]>:
> >
> > Prelude> import Numeric
> > Prelude Numeric> fst $ head $ readFloat "0.1234" :: Rational
> > 617 % 5000
> >
> > On Fri, Feb 24, 2017 at 1:17 PM, Olaf Klinke <[hidden email]> wrote:
> > Dear cafe,
> >
> > when processing text files containing numbers of the form "xxxx.yyyy" I used to parse them into Double using that type's Read instance. Obviously, even with arithmetic no more complicated than the field operations the result might have ugly rounding errors like 12.000000000002 due to the fact that numbers like 0.7 are not dyadic rationals. The math in my program is not complicated and the numbers are not large, so I don't care about Rationals having potentially huge memory footprints.
> >
> > So here's my question. A literal like 0.7 has type Fractional a => a, but the Read instance of Rational rejects the string "0.7". Must it be this way? Do I have to go via toRational.(read :: String -> Data.Scientific.Scientific)?
> >
> > Note that the documentation of Data.Scientific explicitly states that using (/) is unsafe, so I'd rather stay with the field Rational.
> >
> > For the output as decimal expansion, there is of course long division as described here [1], but I wonder whether either this exists in some library or there is even a more efficient solution.
> >
> > Any pointers are appreciated.
> > Thanks,
> > Olaf
> >
> > [1] http://stackoverflow.com/questions/30931369/how-to-convert-a-rational-into-a-pretty-string
> > _______________________________________________
> > 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.

_______________________________________________
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.
Reply | Threaded
Open this post in threaded view
|

Re: reading and writing Data.Ratio.Rational

wren romano
If you're concerned about performance, you should take a look at
bytestring-lexing[1]. The `readDecimal` function does the basic "parse
as a pair of ints then divide" trick, whereas `readDecimalLimited`
does some other tricks to take advantage of types with limited
precision— but which can still give massive performance improvements
for types with unlimited precision, in certain circumstances. If you
want to read the exponential notation rather than just the decimal
notation, then there's also `readExponential` and
`readExponentialLimited`. And there are benchmarks[2] comparing them
to other parsing/lexing libraries.

[1] <http://hackage.haskell.org/package/bytestring-lexing-0.5.0.2/docs/Data-ByteString-Lex-Fractional.html>

[2] <http://community.haskell.org/~wren/bytestring-lexing/bench/html/>

--
Live well,
~wren
_______________________________________________
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.