Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > Ruby > float precision

Reply
Thread Tools

float precision

 
 
Difei Zhao
Guest
Posts: n/a
 
      09-12-2008
Hi all,

Is there a direct method to get something like:

var = sprintf("%.2f", 92.22312).to_f

Thanks alot!

Difei
--
Posted via http://www.ruby-forum.com/.

 
Reply With Quote
 
 
 
 
thomas peklak
Guest
Posts: n/a
 
      09-12-2008
The round function in the float class does not provide a precision
feature, but you can do something like:
(100*9.23234234234532).round/100.0

According to my benchmarks this is at least 1/3 faster than your
approach

Thomas
 
Reply With Quote
 
 
 
 
Difei Zhao
Guest
Posts: n/a
 
      09-12-2008
thomas peklak wrote:
> The round function in the float class does not provide a precision
> feature, but you can do something like:
> (100*9.23234234234532).round/100.0
>
> According to my benchmarks this is at least 1/3 faster than your
> approach
>
> Thomas


thanks for the sharing.
--
Posted via http://www.ruby-forum.com/.

 
Reply With Quote
 
Michael W. Ryder
Guest
Posts: n/a
 
      09-12-2008
thomas peklak wrote:
> The round function in the float class does not provide a precision
> feature, but you can do something like:
> (100*9.23234234234532).round/100.0
>
> According to my benchmarks this is at least 1/3 faster than your
> approach
>
> Thomas


Just out of curiosity, does it make any difference on benchmarks with
Ruby using division versus multiplication? It used to be much faster to
multiply by .01 than divide by 100. I don't know if this has changed
with newer processors and compilers.
 
Reply With Quote
 
thomas peklak
Guest
Posts: n/a
 
      09-13-2008
You are right, multiplying with 0.01 is even fast, see the benchmarks:

require 'benchmark'

times = 1000000
float = 9.234234765765765764
Benchmark.bm do |r|
r.report('SPf :') {
times.times do
f1 = sprintf('%.2f' ,float).to_f
end
}
r.report('*100 :') {
times.times do
f2 = (100 * float).round/100.0
end
}
r.report('*.01 :') {
times.times do
f3 = (100 * float).round*0.01
end
}
end

user system total real
SPf : 5.590000 0.050000 5.640000 ( 5.720373)
*100 : 3.760000 0.040000 3.800000 ( 3.829771)
*.01 : 1.770000 0.010000 1.780000 ( 1.811917)

Thomas
 
Reply With Quote
 
Michael W. Ryder
Guest
Posts: n/a
 
      09-14-2008
thomas peklak wrote:
> You are right, multiplying with 0.01 is even fast, see the benchmarks:
>


Thanks for the information. It looks like multiplication is still twice
as fast as division. I am sure that with today's computers this only
matters with large numbers of operations but on a IBM PC-1 it made a lot
of difference.


> require 'benchmark'
>
> times = 1000000
> float = 9.234234765765765764
> Benchmark.bm do |r|
> r.report('SPf :') {
> times.times do
> f1 = sprintf('%.2f' ,float).to_f
> end
> }
> r.report('*100 :') {
> times.times do
> f2 = (100 * float).round/100.0
> end
> }
> r.report('*.01 :') {
> times.times do
> f3 = (100 * float).round*0.01
> end
> }
> end
>
> user system total real
> SPf : 5.590000 0.050000 5.640000 ( 5.720373)
> *100 : 3.760000 0.040000 3.800000 ( 3.829771)
> *.01 : 1.770000 0.010000 1.780000 ( 1.811917)
>
> Thomas

 
Reply With Quote
 
Robert Klemme
Guest
Posts: n/a
 
      09-16-2008
2008/9/13 thomas peklak <(E-Mail Removed)>:
> You are right, multiplying with 0.01 is even fast, see the benchmarks:
>
> require 'benchmark'
> user system total real
> SPf : 5.590000 0.050000 5.640000 ( 5.720373)
> *100 : 3.760000 0.040000 3.800000 ( 3.829771)
> *.01 : 1.770000 0.010000 1.780000 ( 1.811917)


It's even more efficient to calculate with the full precision and
round only on output.

Cheers

robert


--
use.inject do |as, often| as.you_can - without end

 
Reply With Quote
 
Ted Flethuseo
Guest
Posts: n/a
 
      03-03-2011
Robert Klemme wrote in post #727777:
> 2008/9/13 thomas peklak <(E-Mail Removed)>:
>> You are right, multiplying with 0.01 is even fast, see the benchmarks:
>>
>> require 'benchmark'
>> user system total real
>> SPf : 5.590000 0.050000 5.640000 ( 5.720373)
>> *100 : 3.760000 0.040000 3.800000 ( 3.829771)
>> *.01 : 1.770000 0.010000 1.780000 ( 1.811917)

>
> It's even more efficient to calculate with the full precision and
> round only on output.
>
> Cheers
>
> robert


This doesn't seem to work for certain numbers though... is there a way
to round this 7.17... e+25:

puts "#{cd}\t#{(100 * thr.max).round*0.01}"

output ..

1000 7.17897987691824e+25
200 3.35
4000 0.99
20000 0.69

--
Posted via http://www.ruby-forum.com/.

 
Reply With Quote
 
Joshua S.
Guest
Posts: n/a
 
      04-27-2011
Not surprisingly, it's extremely quicker to convert to a string and
match a regular expression.

user system total real
spf : 1.560000 0.000000 1.560000 ( 1.557252)
*100 : 0.320000 0.000000 0.320000 ( 0.322573)
*.01 : 0.350000 0.000000 0.350000 ( 0.343289)
regex: 0.000000 0.000000 0.000000 ( 0.000019)

The expression
(^-?\d+(\.\d{1,2})?) matches all the following:

12
1.2
1.234567890
12.34567890
123.4567890
1234.567890
-12
-1.2
-1.234567890
-12.34567890
-123.4567890
-1234.567890

-----

require 'benchmark'

times = 1000000
float = 9.234234765765765764
Benchmark.bm do |r|
r.report('spf :') {
times.times do
f1 = sprintf('%.2f' ,float).to_f
end
}
r.report('*100 :') {
times.times do
f2 = (100 * float).round/100.0
end
}
r.report('*.01 :') {
times.times do
f3 = (100 * float).round*0.01
end
}
r.report('regex:') {
f4 = float.to_s.match(/(^-?\d+(\.\d{1,2})?)/)[1].to_f
}
end

--
Posted via http://www.ruby-forum.com/.

 
Reply With Quote
 
Brian Candler
Guest
Posts: n/a
 
      04-28-2011
Joshua S. wrote in post #995421:
> Not surprisingly, it's extremely quicker to convert to a string and
> match a regular expression.
>
> user system total real
> spf : 1.560000 0.000000 1.560000 ( 1.557252)
> *100 : 0.320000 0.000000 0.320000 ( 0.322573)
> *.01 : 0.350000 0.000000 0.350000 ( 0.343289)
> regex: 0.000000 0.000000 0.000000 ( 0.000019)


You should be suspicious of a result which indicates it's 5 orders of
magnitude faster.

> r.report('regex:') {
> f4 = float.to_s.match(/(^-?\d+(\.\d{1,2})?)/)[1].to_f
> }


Ahem, you forgot the "times.times do...end" loop in the benchmark

--
Posted via http://www.ruby-forum.com/.

 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Float precision and float equality Anton81 Python 26 12-11-2009 08:37 AM
float to string to float, with first float == second float Carsten Fuchs C++ 45 10-08-2009 09:47 AM
Arbitrary precision binary float class Thinkit Java 8 12-24-2003 12:26 AM
Selectable precision binary float class? Thinkit Java 2 11-28-2003 09:47 PM
Re: float->byte->float is same with original float image. why float->ubyte->float is different??? bd C Programming 0 07-07-2003 12:09 AM



Advertisments