Oops: Was: Re: working with NSDecimalNumber and NSNumber
Oops: Was: Re: working with NSDecimalNumber and NSNumber
- Subject: Oops: Was: Re: working with NSDecimalNumber and NSNumber
- From: William Squires <email@hidden>
- Date: Sun, 2 Jul 2006 22:17:51 -0500
On Jul 2, 2006, at 7:05 PM, William Squires wrote:
On Jun 24, 2006, at 5:01 PM, Derrick Bass wrote:
On Jun 23, 2006, at 10:34 AM, email@hidden wrote:
Hi list
I was wondering what was the most efficient way to process
calculations between an NSNumber and an NSDecimalNumber
should I use :
NSNumber *myNormalNumber;
NSDecimalNumber *myDecimalNumber;
[...]
myDecimalNumber = [myDecimalNumber
decimalNumberByMultiplyingBy:[NSDecimalNumber
decimalNumberWithString:[myNormalNumber stringValue]]];
or
myDecimalNumber = [myDecimalNumber
decimalNumberByMultiplyingBy:[NSDecimalNumber
decimalNumberWithDecimal:[myNormalNumber decimalValue]]];
(documentation says that decimalValue's value returned isn’t
guaranteed to be exact for float and double values)
Right, that's because floats and doubles are base-2 while
NSDecimalNumber is base-10. Now it is possible to represent any
base-2 value exactly as an decimal number, but NSDecimalNumber
doesn't have enough precision to be able to do that always for
doubles. Moreover, it is likely that whatever is in your float or
double is rounded off already. You won't get any more precision by
converting to strings (less, I should think). If you really need to
multiply by a non-integer float or double, there's really nothing to
be done; you'll just have to accept the precision loss.
And, actually, this occurs even in real life, not just in computers.
Any (real) number has to be representable in some base >= 2. The
number will be exactly representable in that base as long as its
factors are multiples of the base.
So any rational number n/d will be exactly representable in base 10
as long as both 'n' and 'd' have factors of 2 and or 5, or integral
powers thereof. Ditto for some other base. So 1/3 isn't exactly
representable as a decimal (base 10) number because 3 isn't a factor
of 10.
Oops, this should have said, "as long as 'd' has factors of 2 and/or
5...". Clearly any integer (the numerator 'n') can be represented in
any base as long as you have the bits or digits or whatever, to hold
it... Its the fractional part that'll throw you for a loop.
So the only way to represent ANY real number without losing
precision would be to use base infinity, which would clearly be
impractical! :)
Furthermore, why p*ss around with NSNumbers and such if you're
dealing with currency? Just convert the numbers to cents and store in
a long int. Do the calculations there (a lot faster), then convert
back to an NSNumber or NSDecimalNumber, remembering that you're
storing cents, not dollars.
The same goes for other nation's currencies - just represent the
smallest denomination in an integral data type.
Be careful multiplying (or dividing) fractions (like when
calculating interest, APR, etc...) For example: 3 cents x 3 cents is
clearly 9 cents, but $0.03 x $0.03 = $0.0009, or 9 one-hundredths of a
penny. Whoops.
or should I use parent methods From NSNumber like numberWithFloat:
?
I use NSDecimalNumber for money related values so my calculations
need to be as precise as possible ...
Are you sure you aren't actually multiplying by a decimal number? If
so, then you should represent it exactly in an NSDecimalNumber. If
your numbers really are floats (like from an interest calculation)
then you'll have to decide upon an appropriate rounding scheme. And
if it really is a decimal number, but you just can't help the fact
that it is represented by a float/double, then convert it to an
NSDecimalNumber and round it to the correct number of places before
calculating with it.
Derrick
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Cocoa-dev mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
email@hidden
This email sent to email@hidden
William H Squires Jr
4400 Horizon Hill #4006
San Antonio, TX 78229
email@hiddenm <- remove the .nospam
William H Squires Jr
4400 Horizon Hill #4006
San Antonio, TX 78229
email@hiddenm <- remove the .nospam
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Cocoa-dev mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden