Forum: RSpec any tricks re using " eql(5.5)", but where 5.5 is a decimal not float?

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-08 00:43
(Received via mailing list)
--
Sent from my mobile device
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-08 00:45
(Received via mailing list)
(woops - full email below)

Hi,

My rails migrations / mysql database uses Decimal and I've noticed in
my rspec when I do a "...should eql(5.5)" that they're failing as the
expected result here is a float not a decimal.  For example see
extract below:

     expected 6.5, got #<BigDecimal:23d8284,'0.65E1',8(8)> (using .eql?)

What's the best way of addressing this?  Is there trick regarding the
easiest way to address this?

Thanks




On Sat, Nov 8, 2008 at 9:18 AM, Greg Hauptmann
48641c4be1fbe167929fb16c9fd94990?d=identicon&s=25 Mark Wilden (Guest)
on 2008-11-08 00:53
(Received via mailing list)
On Fri, Nov 7, 2008 at 3:24 PM, Greg Hauptmann <
greg.hauptmann.ruby@gmail.com> wrote:

>
>     expected 6.5, got #<BigDecimal:23d8284,'0.65E1',8(8)> (using .eql?)
>

How about just expecting BigDecimal('5.5')?

///ark
48641c4be1fbe167929fb16c9fd94990?d=identicon&s=25 Mark Wilden (Guest)
on 2008-11-08 00:55
(Received via mailing list)
There's my C roots showing. :) That should be BigDecimal.new('5.5'), of
course.
42172acdf3c6046f84d644cb0b94642c?d=identicon&s=25 Pat Maddox (pergesu)
on 2008-11-08 00:59
(Received via mailing list)
"Greg Hauptmann" <greg.hauptmann.ruby@gmail.com> writes:

Do you mean BigDecimal?  Anyway, you should probably be using == instead
of eql.

>> 5.5 == BigDecimal.new('5.5')
=> true
>> 5.5.eql? BigDecimal.new('5.5')
=> false

eql? is object identity and is generally not what you're after.

Pat
48641c4be1fbe167929fb16c9fd94990?d=identicon&s=25 Mark Wilden (Guest)
on 2008-11-08 01:40
(Received via mailing list)
On Fri, Nov 7, 2008 at 3:51 PM, Pat Maddox <pergesu@gmail.com> wrote:

> eql? is object identity and is generally not what you're after.
>

Yeah, but

>> BigDecimal('5.5').eql? BigDecimal('5.5')
=> true

So it's either creating value objects (like Symbol) or BigDecimal.eql?
doesn't do object equality.

What's interesting is that you can create BigDecimals this way (without
calling new). You can do it with Strings, too.

>> String('asdf')
=> "asdf"

But not everything:

>> Hash(:a => 5)
NoMethodError: undefined method `Hash' for #<Object:0x3799c>
    from (irb):12

As Johnny Carson used to say, "I did not know that."

///ark
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-08 02:37
(Received via mailing list)
in fact I guess I was fishing for an easier way than this...if one
exists?  or is ruby & rspec "eql()" just strict here in terms of
types?
F86901feca747abbb5c6c020362ef2e7?d=identicon&s=25 Zach Dennis (zdennis)
on 2008-11-08 02:49
(Received via mailing list)
On Fri, Nov 7, 2008 at 6:24 PM, Greg Hauptmann
<greg.hauptmann.ruby@gmail.com> wrote:
>
> What's the best way of addressing this?  Is there trick regarding the
> easiest way to address this?

You aren't by chance using decimals to represent money are you?

--
Zach Dennis
http://www.continuousthinking.com
http://www.mutuallyhuman.com
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-08 03:21
(Received via mailing list)
yep - this was recommended on forums over float - why?
F86901feca747abbb5c6c020362ef2e7?d=identicon&s=25 Zach Dennis (zdennis)
on 2008-11-08 03:24
(Received via mailing list)
On Fri, Nov 7, 2008 at 9:12 PM, Greg Hauptmann
<greg.hauptmann.ruby@gmail.com> wrote:
> yep - this was recommended on forums over float - why?

You are in for a lot of headaches in you application resorting to
decimal fields in the database, since it restores them as BigDecimals.
It sucks to deal with BigDecimals in your app. I very highly recommend
the Money library. I recommend installing it as a plugin and using the
CollectiveIdea fork.

http://github.com/collectiveidea/money/tree/master

Even if all you do is take 20 minutes to check out the Money library
in a dummy app, I think you will be glad you did.

Zach


>>> expected result here is a float not a decimal.  For example see
>> Zach Dennis
>> http://www.continuousthinking.com
>> http://www.mutuallyhuman.com
>> _______________________________________________
>> rspec-users mailing list
>> rspec-users@rubyforge.org
>> http://rubyforge.org/mailman/listinfo/rspec-users
>>
>



--
Zach Dennis
http://www.continuousthinking.com
http://www.mutuallyhuman.com
42172acdf3c6046f84d644cb0b94642c?d=identicon&s=25 Pat Maddox (pergesu)
on 2008-11-08 05:26
(Received via mailing list)
"Greg Hauptmann" <greg.hauptmann.ruby@gmail.com> writes:

>>>
>>
>> How about just expecting BigDecimal('5.5')?
>>
>> ///ark
>>

I'm not sure if you got my email before, but 6.5 ==
BigDecimal.new('6.5').  So use == instead and you should be good.

Pat
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-08 06:53
(Received via mailing list)
thanks Pat - yes I missed it when reading your email - I'd been using
".eql" for everything....thanks
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-08 07:44
(Received via mailing list)
very bizzare but whilst I needed to use this approach to fix one of my
tests, I realised the test before was working without having to make
it a big decimal - go figure   :)

  --------------------------------
  it "should return last IR when date > last interest rate" do
    @source_bank.ir(Time.now.to_date + 1.years).should == 8.5  # <==
WORKED FINE
  end

  it "should return latest IR not greater than date specified when a
date is passed" do
    @source_bank.ir(Time.now.to_date + 8.days).should ==
BigDecimal.new('6.5') # <== NEEDED TO USE BigDecimal here
  end
  --------------------------------


On Sat, Nov 8, 2008 at 3:37 PM, Greg Hauptmann
2ce9c0106b5851b2294ba5eb9f5c04bd?d=identicon&s=25 Ashley Moran (Guest)
on 2008-11-09 13:29
(Received via mailing list)
On Nov 08, 2008, at 2:18 am, Zach Dennis wrote:

> <greg.hauptmann.ruby@gmail.com> wrote:
>> yep - this was recommended on forums over float - why?
>
> You are in for a lot of headaches in you application resorting to
> decimal fields in the database, since it restores them as BigDecimals.
> It sucks to deal with BigDecimals in your app. I very highly recommend
> the Money library. I recommend installing it as a plugin and using the
> CollectiveIdea fork.


Ha, I wrote the ActiveRecord patch so this was possible :)

The reason for storing monetary values as SQL decimals is that they
aren't subject to rounding errors[1].  I used to work in the finance
sector, and it was absolutely unacceptable to expose financial
calculations to these errors.  Hence I added support in ActiveRecord
so we could use Rails; it was just not an option otherwise.

The decision you have to make is between the extra effort now of using
decimals in your code vs the extra effort later of explaining to your
users why your calculations sometimes come out wrong.  And that
depends on how much your users value knowing that these figures are
correct.

Ashley


[1]
http://www.theregister.co.uk/2006/08/12/floating_p...

--
http://www.patchspace.co.uk/
http://aviewfromafar.net/
D5df9fcd7ef4c3c937435d7d6adeab2a?d=identicon&s=25 Greg Hauptmann (Guest)
on 2008-11-10 01:23
(Received via mailing list)
Ashley - what's you're recommendation re using BigDecimal (which does
work as you point out) and the Money gem (which it sounds like makes a
dev's life a bit easier)???  Is it worth trying to port an application
from use of BigDecimal to Money gem???

On Sun, Nov 9, 2008 at 10:27 PM, Ashley Moran
2ce9c0106b5851b2294ba5eb9f5c04bd?d=identicon&s=25 Ashley Moran (Guest)
on 2008-11-10 12:12
(Received via mailing list)
On Nov 10, 2008, at 12:21 am, Greg Hauptmann wrote:

> Ashley - what's you're recommendation re using BigDecimal (which does
> work as you point out) and the Money gem (which it sounds like makes a
> dev's life a bit easier)???  Is it worth trying to port an application
> from use of BigDecimal to Money gem???


Hi Greg

I'd use the money gem if and only if it's underlying implementation is
BigDecimal or some other fixed-precision system.  I've had a look over
it and it appears to use integers to store values as small as 1/100 of
the base unit.  So as long as you don't need to use anything smaller
than that in calculations (ie, you only add, and never multiply,
values - eg for tax calculations) it will be fine.

I'll try not to say too much more, we're straying well away from RSpec
territory...

Ashley

--
http://www.patchspace.co.uk/
http://aviewfromafar.net/
This topic is locked and can not be replied to.