Search code examples
c#asp.netintegerinteger-overflow

C# "Integral constant is too large" - Integer variable too large for Int32 type


I'm building an ASP.NET Core API that returns the periodic table and the planets in the solar system. Mainly to play with API calls, as well as data types in .NET. Building this in Visual Studio 2017.

I'm having problems with a Mass property for planets, in Kilograms. Obviously a large integer, so I've tried declaring it as a long, Ulong, Int64, and even UInt64. However, when I try to enter in a new model of a planet, and put in the mass, I get the following error:

struct System.Int32
Represents a 32 bit signed integer.
Integral constant is too large.

Here is my PlanetModel.cs where I'm describing the property:

...
public UInt64 Volume { get; set; } //In Kilometers
public Int64 Mass { get; set; } //In Kilograms
public float Gravity { get; set; } //In m/s^2
...

Yet when I move over to my PlanetDataStore.cs, here is where I'm trying to build the object with data.

new PlanetModel()
                {
                    Position = 1,
                    Name = "Mercury",
                    Distance = 57909050, //In Kilometers
                    Orbit = 0.240846F, //In years
                    SolarDay = 0.5F, //In Days
                    Radius = 2439, //In Kilometers
                    Volume = 60830000000, // In Kilometers
                    Mass = 330110000000000000000000, //In Kilograms
                    Gravity = 3.7F, //In m/s^2
                },

I get a red error squiggly over the first '3' in my Mass, with the error above. Yet when I mouse over Mass, it reads: "long PlanetMode.Mass {get; set;} When I mouse over the equals, it reads: "struct System.Int64"

Where is the miscommunication? Why is my property declared as a 64-bit integer, but the value stuck in 32-bit?


Solution

  • Obviously a large integer

    That is by no means obvious. The mass of the earth is not an integral number of kilograms. You shouldn't be using any integral type for this application. Use integers for things that are genuinely integers, like the number of elements in a sequence.

    Use double for physical quantities that are accurately measured to ten-ish decimal places. Mass, volume, length, force, and so on, should always be doubles.

    This will also let you get rid of those hard-to-read numbers. Doubles let you use scientific notation because doubles are for science:

    Mass = 3.3011E23,
    

    Also, while we're looking at your solution, I note that for spherical planets, the volume can be computed from the radius. You might not want to store both; instead, just store one and calculate the other when you need it.

    I note also that you have a single "distance" which seems to be the semi-major axis in the case of Mercury. Why are you storing only the semi-major axis, and why not call it what it is?

    I note also that you have mixed up your units all over the place -- meters and kilometers, days and years, and so on. Why not keep everything in standard units? Meters for length, seconds for time, kilograms for mass. You'll find that you make fewer silly arithmetic mistakes when you use standard units consistently.