Integer math vs. floating point for physics variables

Started by
6 comments, last by SpaceRogue 20 years, 11 months ago
How does everyone avoid the problems caused by lack of precision in floating point variables with large values? Example: I want to create a large game world for a space sim, but one that has reasonable detail at human scale distances as well. Using variables of type double for objects'' x,y,z coordinates results in bizarre behavior when you are far from the coordinate system''s origin due to the loss of precision digits behind the decimal point. Integer types don''t have this problem, but present their own...i.e. inherent lack of precision with any kind of divide operation. So, what''s a good solution? I''m considering using double for all my variables, like velocity, etc. but sticking to integers for my global coordinates. The only disadvantage I see here is loss of speed in static_casting my velocity to integer changes in position. Would that be a significant speed loss?
Advertisement
You have a couple of options for >32 bit math on current PCs.

1) Use 64 bit integer math: not too hard, as long as you know how to implement fixed precision integer math.

2) Make some arbitrary precision math library: this is probably the most complicated method to implement, but if you can find one floating around the web (programmersheaven.com maybe?)

3) 64 bit floating point math: real easy to use

4) 80 bit floating point math: again easy

I would suggest you use 64 bit floating point (double) and/or 80 (long double) bit. You shouldn''t need anything higher than that. If you do I suggest you re-think your game design. Anything higher is in the realm of scientific simultations, which are too slow for most games. Unless your a pretty darn good programmer (ie. good with assembly, and also probably not asking a question like this) then any integer implementation would certainly be slower then any floating point implementation. All the compilers I know of (I don''t think the Vector C ones does either without explicite hints) won''t take into account the sse registers and sse2 instruction set which are what would be needed to do >64 bit integer precision at any decent speed. One thing to also keep in mind, all this only applies to physical simoulations, all object geometry / graphical data should always be stored using 32 bit floating point as current hardware acceleration dictates such.
iirc sean o''neils tuts here on gamedev deal with this problem to a certain extent, you can find them somewhere in the articles section

"We are what we repeatedly do. Excellence, then, is not an act, but a habit." - Aristotle
http://fusi.basscut.net"We are what we repeatedly do. Excellence, then, is not an act, but a habit." - Aristotle

Thanks, but I''m not looking for anything larger than 64 bit integers or floating points.

Hmm, maybe I can explain better with an example:

Since this is a space sim, it involves very large distances, but ones within 32 or 64 bit ranges. Say we choose our x,y,z coordinates as type double variables, and decide on a unit of 1 kilometer. Now double only has 15 digits of precision despite its huge range. Now if we have an object very far from the origin, say millions of kilometers, then collision detection against (or even rendering of) the ships geometry could very well suffer because of round off error in the floating point coordinates. See what I mean?

You can get around this by using integer coordinates, but integer velocities, and accelerations don''t make for very accurate physics, so you end up casting from floating point types (used internally for physics) to integer types for position, and probably casting back to a float for rendering (as you pointed out). Does this impact speed much? Is using an integer coordinate system, while using floats everywhere else a problem? Does no one else use such large distances or do people just fudge numbers a lot?

Thanks Fusi0n.

I can''t check the tutorials out right now...since I don''t have my gamasutra login info with me at work, but I''ll check them out later.
quote:Original post by SpaceRogue
... Is using an integer coordinate system, while using floats everywhere else a problem? Does no one else use such large distances or do people just fudge numbers a lot?


You can change what the location is relative to. So, when a ship leaves one area, you just convert the location to be relative to some other point in space, and continue along.
As long as you can calculate the relative distance from one thing to another, between objects using different origins, then you are fine.
Split your world into a grid of cubes. Store your coordinates as a 32-bit triple of cube x/y/z coordinates, and a float for offset within the cube. Supposing you want one-tenth of a millimeter in resolution, that''ll take about 14 bits of the 24 available in a float, giving you one kilometer per cube. So you get 4 billion kilometer-size cubes going along each axis -- should be sufficient for most needs.

If you need more than that, use int64-s for the cube coordinates.
You can also try using distances in different units, depending on what you are doing. For instance, for planetary distances use AU''s or megakilometers. Basically any time your numbers seem to grow past a certian huge amount, switch them down to a smaller unit. Also, use more relative positions as someone said. You DON''T want to do things like 100000000000000001 - 1000000000000002 when you should just be doing 1-2.

This topic is closed to new replies.

Advertisement