On 11/29/2012 11:06 AM, Stephen Bloch wrote:
On Nov 29, 2012, at 9:44 AM, Greg Graham wrote:
I am trying to report GPA calculation results to 2 decimal places, so I thought
real->decimal-string would do the trick. However, the following behavior
surprised me:
(real->decimal-string 3.225 2)
"3.23"
(real->decimal-string 4.225 2)
"4.22"
I would like the second answer to be "4.23", which is what a student would expect
to see if they did the calculations themselves. The documentation for
real->decimal-string says that it first converts the argument to an exact number. I
suspect the problem has something to do with this:
(inexact->exact 4.225)
4 126663739519795/562949953421312
(/ 126663739519795.0 562949953421312.0)
0.22499999999999964
Is there another rounding function that would just round the floating point
without going through the conversion to exact?
Another rounding function won't help, because by the time the READER has finished with
the character string "4.225", the internal form is already slightly less than
4225/1000. And if you're getting the inexact 4.225 from somewhere else, again it's not
really 4225/1000 so it's already too late to round it the way you want.
You could work in a student language, where the reader reads decimals as exact
by default :-)
Seriously, I'm sure there's a way to tell the reader in other languages to read
decimals as exact; I just don't know what it is.
Prefix the number with "#e", as in
> #e4.225
169/40
As an alternative, you could create a language that sets the
'read-decimal-as-inexact' reader parameter to #f before reading the
module contents. Try saving the following as s-exp-exact/lang/reader.rkt
(adapted from s-exp/lang/reader.rkt with some help from Carl):
(module reader syntax/module-reader
#:language (lambda (p) (read-syntax (object-name p) p))
#:wrapper1 (lambda (go)
(parameterize ((read-decimal-as-inexact #f)) (go))))
Then run
#lang s-exp-exact racket
(exact? 4.225)
Ryan
____________________
Racket Users list:
http://lists.racket-lang.org/users