473,787 Members | 2,931 Online
Bytes | Software Development & Data Engineering Community
+ Post

Home Posts Topics Members FAQ

double trouble

I have a not-so-large double in the range 1-1000, but with fractional
part. I only do ++my_double to increment it, however sometimes it
happens that after incrementing

int(old_double) == int(new_double)

why? Again the doubles are not large at all, their exponents cannot be
so high to shift out the 1 I add out when incrementing and we have 64
bits to use here.
Feb 23 '07 #1
5 1949
On Feb 23, 12:08 pm, John Doe <NOTOSPAMjohndo e64...@yahoo.co mwrote:
I have a not-so-large double in the range 1-1000, but with fractional
part. I only do ++my_double to increment it, however sometimes it
happens that after incrementing

int(old_double) == int(new_double)

why? Again the doubles are not large at all, their exponents cannot be
so high to shift out the 1 I add out when incrementing and we have 64
bits to use here.
It's kind of hard to know without some code sample
that shows the behaviour. But it's just possible that
the ++ operation took you from <number that is so close
to integer N that it is indistinguishab le to the int()>
to <number that is very close to N+1, but just enough
smaller that it is distinguishable to int()>.

I'm guessing that you are working with numbers that are
quite close to integer values.

Don't forget that doubles are stored in a floating point
format. It may be that you have found one of those spots
where you can't perfectly represent a real number as a
floating point. You may think you've got a slightly
smaller number for the old than you really do, and
you may think you've got a slightly larger value for
the new than you really do.

Generally speaking, you should be doing a different kind
of compare, if you really must compare floating point
values. You should be defining some kind of tolerance
for equality, then checking if the difference is less
than this tolerance. And you should be aware of such
issues as loss of accuracy due to subtracting numbers
that are very close to eachother.
Socks

Feb 23 '07 #2
John Doe wrote:
I have a not-so-large double in the range 1-1000, but with fractional
part. I only do ++my_double to increment it, however sometimes it
happens that after incrementing

int(old_double) == int(new_double)

why? Again the doubles are not large at all, their exponents cannot be
so high to shift out the 1 I add out when incrementing and we have 64
bits to use here.
First of all, a nit pick: you most likely only have 53 bits, not 64.
Second, can you provide a concrete example? And how do you know that
int(before) == int(after)? By looking at it in the debugger? The
only case I know where it would be true if the double in on (-1,0) to
begin with.

V
--
Please remove capital 'A's when replying by e-mail
I do not respond to top-posted replies, please don't ask
Feb 23 '07 #3
John Doe wrote:
I have a not-so-large double in the range 1-1000, but with fractional
part. I only do ++my_double to increment it, however sometimes it
happens that after incrementing

int(old_double) == int(new_double)

why? Again the doubles are not large at all, their exponents cannot be
so high to shift out the 1 I add out when incrementing and we have 64
bits to use here.
Casting to int truncates the fractional part. Some values do
not have a finite representation in binary format and so cannot
be stored in a double with infinite accuracy. I imagine the
scenario is something like (though not for number 42):

double x=42; // actually becomes x=42.0000000000 0001
int y=(int)x; // the fractional part is truncated, y becomes 42.
x++; // actually becomes x=42.9999999999 9999
int z=(int)x; // the fractional part is truncated, z becomes 42.
z==y; // true

... but this is just guessing.

HTH,
- J.
Feb 23 '07 #4
Jacek Dziedzic wrote:
John Doe wrote:
>I have a not-so-large double in the range 1-1000, but with fractional
part. I only do ++my_double to increment it, however sometimes it
happens that after incrementing

int(old_double ) == int(new_double)

why? Again the doubles are not large at all, their exponents cannot
be so high to shift out the 1 I add out when incrementing and we
have 64 bits to use here.

Casting to int truncates the fractional part. Some values do
not have a finite representation in binary format and so cannot
be stored in a double with infinite accuracy. I imagine the
scenario is something like (though not for number 42):

double x=42; // actually becomes x=42.0000000000 0001
That is very unlikely. Integers of this magnitude are represented
precisely in IEEE floats. It could be after some kind of imprecise
calcuation, of course.
int y=(int)x; // the fractional part is truncated, y becomes 42.
x++; // actually becomes x=42.9999999999 9999
That is not possible. How can adding 1 screw up the mantissa so
badly? See my analysis below.
int z=(int)x; // the fractional part is truncated, z becomes 42.
z==y; // true

... but this is just guessing.
Yep.

What's going on with the number when you add 1?

Before adding the FP number can be written (in binary form) as

1bbbbbb.bbbbbbb bbbbbbB (total of N binary digits)
^^^^^^^
K digits before binary point. 'B' is the last binary digit
in the representation.

After adding 1 we could have either

10000000.bbbbbb bbbbbbbb (total of N binary digits)
^^^^^^^
K zeros

which would mean the last digit ('B') is lost or rounded to make
the fraction slightly different. If it's rounded "down", it is
the same as throwing it out. If it's rounded up, you can end up
with a fraction that when rounded eventually turns into another 1
and is added to the integral part (for that you need the fractional
part full of 1s). In either case adding 1 cannot mean retaining
the integral part (it either grows by 1 or by 2).

We could have (after adding 1)

1bbbbbb.bbbbbbb bbbbbbB (total of N binary digits)
^^^^^^^
K (slightly different) digits before binary point. 'B' is
still the last binary digit, in which case the fraction does not
change at all, and simply cannot contribute to changing the
integral part.

V
--
Please remove capital 'A's when replying by e-mail
I do not respond to top-posted replies, please don't ask
Feb 23 '07 #5
You were right c++ wizards:

x started low ~-1e-14, adding 1 to this produced, 0.something very close
to 1, but int(old_double) == int(new_double) . Then there was additional
trouble: adding 1 to this repeatedly was producing numbers very close to
round(x) integers and then suddenly adding 1 rounded a
number_close_to _an_integer upwards and 1 integer was skipped by int(x),
say if you had

511.99999999999 999999999

int() would produce 511, but if you'd add 1 to this and hence shifted it
right sufficient places, you might produce 513, instead of
512.99999999999 999999999.

Anyway, std::round(x) solved my problem, thank you.
Feb 23 '07 #6

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

10
1922
by: Jacek Dziedzic | last post by:
Hi! Let's say I have a class called Triplet that serves as an envelope for double, ie. class Triplet { public: Triplet() {/*...*/} /* some things that double doesn't have, like
10
8662
by: Robert Palma | last post by:
I'm having trouble figuring out how to pass a pointer to a double array (1 dimensional) to a C function. Declaring array as: double xx; Declaring func. int process( double *input ) Calling func. as one of the following:
67
9927
by: lcw1964 | last post by:
This may be in the category of bush-league rudimentary, but I am quite perplexed on this and diligent Googling has not provided me with a clear straight answer--perhaps I don't know how to ask the quesion. I have begun to familiarize myself here with the gcc compiler in a win32 environment, in the form of MinGW using both Dev C++ and MSYS as interfaces. I have recompiled some old math code that uses long double types throughout and...
11
3719
by: Ole Nielsby | last post by:
First, sorry if this is off-topic, not strictly being a C++ issue. I could not find a ng on numerics or serialization and I figure this ng is the closest I can get. Now the question: I want to serialize doubles in human-readable decimal form and be sure I get the exact same binary values when I read them back. (Right now, I don't care about NaN, infinities etc.)
4
4415
by: =?Utf-8?B?cGF0cmlja2RyZA==?= | last post by:
Hi everyone! I'm using greece - greek in my control panel's regional options, and so, my decimal point is the comma (,), while it is the dot (.) for the sql server db, however, I'm facing trouble when I need to parse the sql server decimal as an asp.net double! For example:
10
6608
by: Bo Yang | last post by:
Hi, I am confused by the double type in C++. I don't know whether below is legal or possible: double PI = 3.141592675932; Now, can I get another double variable from PI with lower precision, for example, 3.1415926 . Or, in another way, how does the double presented in computer, and
23
13527
by: dkirkdrei | last post by:
I am having a bit of trouble trying to double up on slashes in a file path. What I am trying to do is very similar to the code below: <? $var = "\\wusais\Intranets\Intranets\fpdb\pdf\weinig\00505882.pdf"; $new = preg_replace("\\", "\\\", "$var"); ?> Code above produces the following error:
3
7231
by: newbtemple | last post by:
Hey all, having some trouble with casting values inputed into a text box into double. In particular, I'm having trouble with the decimal. It's ok if someone puts in a number with a decimal when there is a number before the decimal, but if I input the decimal first I get a : "Make sure your method arguments are in teh right format" error. Private Sub tbPrice_TextChanged(ByVal sender As System.Object, ByVal e As System.EventArgs)...
0
2561
by: Charles Coldwell | last post by:
James Kanze <james.kanze@gmail.comwrites: True, with some additional considerations. The commonly used IEEE 754 floating point formats are single precision: 32 bits including 1 sign bit, 23 significand bits (with an implicit leading 1, for 24 total), and 8 exponent bits double precision: 64 bits including 1 sign bit, 52 significand bits
30
4046
by: copx | last post by:
I am writing a program which uses sqrt() a lot. A historically very slow function but I read on CPUs with SSE support this is actually fast. Problem: C's sqrt() (unlike C++ sqrt()) is defined to work on doubles only, and early versions of SSE did not support double precision. The CPU requirement "something with at least first generation SEE support" (everything from P3/Athlon XP and up) is acceptable for me. However, requiring a CPU which...
0
9655
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However, people are often confused as to whether an ONU can Work As a Router. In this blog post, we’ll explore What is ONU, What Is Router, ONU & Router’s main usage, and What is the difference between ONU and Router. Let’s take a closer look ! Part I. Meaning of...
0
9498
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can effortlessly switch the default language on Windows 10 without reinstalling. I'll walk you through it. First, let's disable language synchronization. With a Microsoft account, language settings sync across devices. To prevent any complications,...
0
10363
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers, it seems that the internal comparison operator "<=>" tries to promote arguments from unsigned to signed. This is as boiled down as I can make it. Here is my compilation command: g++-12 -std=c++20 -Wnarrowing bit_field.cpp Here is the code in...
1
10110
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows Update option using the Control Panel or Settings app; it automatically checks for updates and installs any it finds, whether you like it or not. For most users, this new feature is actually very convenient. If you want to control the update process,...
0
9964
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each protocol has its own unique characteristics and advantages, but as a user who is planning to build a smart home system, I am a bit confused by the choice of these technologies. I'm particularly interested in Zigbee because I've heard it does some...
0
5398
by: TSSRALBI | last post by:
Hello I'm a network technician in training and I need your help. I am currently learning how to create and manage the different types of VPNs and I have a question about LAN-to-LAN VPNs. The last exercise I practiced was to create a LAN-to-LAN VPN between two Pfsense firewalls, by using IPSEC protocols. I succeeded, with both firewalls in the same network. But I'm wondering if it's possible to do the same thing, with 2 Pfsense firewalls...
0
5535
by: adsilva | last post by:
A Windows Forms form does not have the event Unload, like VB6. What one acts like?
2
3670
muto222
by: muto222 | last post by:
How can i add a mobile payment intergratation into php mysql website.
3
2894
bsmnconsultancy
by: bsmnconsultancy | last post by:
In today's digital era, a well-designed website is crucial for businesses looking to succeed. Whether you're a small business owner or a large corporation in Toronto, having a strong online presence can significantly impact your brand's success. BSMN Consultancy, a leader in Website Development in Toronto offers valuable insights into creating effective websites that not only look great but also perform exceptionally well. In this comprehensive...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.