# Why do programming languages usually not implement number types with units?

Summary:
For implementing lets say physical models it would be handy to not only know the numeric value of a variable, but also its units, have all kinds of conversions (fahrenheit to celcius, meters to feet, etc.) and addition/subtraction rules (can only add or subtract values with the same units).
In fact, the only programming language I know of that implements something like units is the programming language Frink.

In other programming languages, the implementation is left to the programmer, for example C++ can implement this as a class.

jbergman, hmmm27 and Jarvis323

jedishrfu
Mentor
Yes that’s true. We often use variable naming conventions to convey the units used and then apply a math conversion to get other units of measure.

in a recent project, we were constantly converting English measure input to metric for modeling and then back to English measure for display.

There are some domain specific languages that do this in their class design so that you can add apples and oranges to get fruit.

z.meters = x.feet + y.yards

in one groovy language domain specific example, I saw pharmacists could use the language to do complicated drug formulations mixing and matching English measure with metric measure.

http://docs.groovy-lang.org/docs/latest/html/documentation/core-domain-specific-languages.html

pbuk
Gold Member
I disagree. When implementing physical models I have found that it is very important to used consistent units throughout the implementation.

Merlin3189, Dr.D and caz
pbuk
Gold Member
in one groovy language domain specific example, I saw pharmacists could use the language to do complicated drug formulations mixing and matching English measure with metric measure.
This would be a good application for mixed units.

I disagree. When implementing physical models I have found that it is very important to used consistent units throughout the implementation.
What do you disagree with? Your reaction in fact supports the position mentioned in the OP, that one would need some (standard or user defined) implementation of units for specific programming cases, like physical models.

caz
Gold Member
It’s computationally expensive. For example, if you are doing time stepping why do you want to carry that information through every step?

pbuk
Gold Member
What do you disagree with?
I disagree that multiple units should be dealt with in the implementation of a physical model. An application that is capable of converting between different units is a completely different thing.

FactChecker and caz
It’s computationally expensive. For example, if you are doing time stepping why do you want to carry that information?
Agree. But the normal number types (without unit information) can be used for such parts of the program. The use case for number types with unit information is for interaction with the user (input/output) and simple calculations. So you could have a program that internally uses meters for length units, while the user interface uses feet or miles.

pbuk
Gold Member
Agree. But the normal number types (without unit information) can be used for such parts of the program. The use case for number types with unit information is for interaction with the user (input/output) and simple calculations. So you could have a program that internally uses meters for length units, while the user interface uses feet or miles.
Precisely. So we deal with the unit conversions in the presentation layer, not the impementation layer (and certainly not embedded in the language).

Merlin3189, FactChecker and caz
caz
Gold Member
Agree. But the normal number types (without unit information) can be used for such parts of the program. The use case for number types with unit information is for interaction with the user (input/output) and simple calculations. So you could have a program that internally uses meters for length units, while the user interface uses feet or miles.
You can then run into issues with significant digits and cutoffs. It’s better to write non-dimensional code where the user only needs to enter self-consistent data (which could be generated by a front end).

Last edited:
jedishrfu
anorlunda
Staff Emeritus
I think it could make a fun student project to implement classes for numbers with units.

The classes could compute the units of a result or do other dimensional analysis.

The classes could catch errors in units (such as adding quantities with different units.)

The classes might perform automatic unit conversion, or forbid unit conversion thus forcing consistent units.

A second run-time version of the classes for runtime could be used after debugging to drop the computationally expensive units and leave just numbers. Or the classes with units might be invoked only during source code editing, but not at runtime.

In other words, make it a feature of the editor, not the language.

I confess, the thought piqued my interest.

Last edited:
elcaro
It’s computationally expensive. For example, if you are doing time stepping why do you want to carry that information through every step?
Can be done at compile time.

jedishrfu and elcaro
Staff Emeritus
Is 2 degrees + 359 degrees 361 degrees? 1 degree? Something else?

Is red + green + blue black, like pigment or white, like light?

I think it's entirely reasonable to make these decisions when building classes and other data structures. I think trying to build this into intrinsic types will create more problems than it solves.

Merlin3189, Astronuc, caz and 1 other person
PeterDonis
Mentor
2020 Award
Summary:: For implementing lets say physical models it would be handy to not only know the numeric value of a variable, but also its units, have all kinds of conversions (fahrenheit to celcius, meters to feet, etc.) and addition/subtraction rules (can only add or subtract values with the same units).
This is a classic case of something that should be implemented as a library, not intrinsic to a programming language. Why? Because different applications will use very different unit systems. Libraries can easily address those different needs. Making units intrinsic to a language would make that harder, not easier.

jedishrfu
Mentor
Using libraries is the most common way. However, a case could be made for subtyping floats and int as units of measure with the compiler validating and autoboxing as needed.

So many times in scientific applications maintained over a long term, the units of measure for data gets lost along with any documentation that explained it thoroughly. Programmers are left to wing it through testing and careful code review to insure that they haven’t affected the data values with their changes.

I’ve seen a few cases where conversions were applied then unapplied then reapplied as the data wended it’s way through the code. In one case, the conversion from English to meters was applied twice giving out some real confusing results. In another case, degrees were confused with radians which produced Spirograph display output.

Naming conventions for variables can sometimes help although @Mark44 can tell the fiasco of Symonyi variable naming notation at his company that drove people mad.

Jarvis323
FactChecker
Gold Member
The program language can use consistent standard units that it works with internally and only needs to convert to other units when it is interfacing with the user or other programs. The MathCad computer software by Mathsoft does that. It is very useful and can assist in dimensional analysis in its operations. It was very helpful. I thought that was where software was headed decades ago.
Then along came Ada. Instead of being helpful, it just refused to compile and taunted you cruelly at every step. We called it "strict typing hell". The result was that unchecked conversion was used far too often just to get something to run. But it often did stop you from adding inches to feet.

Last edited:
Jarvis323
Mark44
Mentor
So we deal with the unit conversions in the presentation layer, not the impementation layer (and certainly not embedded in the language).
Strongly agree.
However, a case could be made for subtyping floats and int as units of measure
Floating point numbers and integral numbers are already subtyped, but on the basis of ranges of values rather than units. For example, in C and C++, there are float, double, and long double for floating point types; there are short, int, long, and long long for integral types, with signed and unsigned versions of each.
Naming conventions for variables can sometimes help although @Mark44 can tell the fiasco of Symonyi variable naming notation at his company that drove people mad.
AKA Hungarian notation (Charles Simonyi is Hungarian). This was more related to the type of the variable, using prepended "warts," and not so much on the units involved in numeric types. For example, Windows code has a lot of variables with names like pszNameStr, where the psz prefix means "pointer to a zero-terminated string."

Baluncore
I have written an overload for BASIC functions that tracks the full dimensional analysis through the computations. It correctly converts to and identifies all SI units and recognises named dimensions.

Such a dimensional analysis only needs to be done once at compile time. I do that by overloading before the run to check my program, or to identify problems.

Once you understand what you are doing, you do not need to use it very often as you perform the dimensional analysis in your subconcious while coding.

Jarvis323
Why do programming languages usually not implement number types with units?
Most programming languages are supposed to be kind of universal, and very few of them is so special that such extravagant functions would be addressed.

I would expect this kind/level of specialization to be possible part of specialized 'languages' dedicated to deal with math or physics problems.

Staff Emeritus
For example, in C and C++, there are float, double, and long double for floating point types; there are short, int, long, and long long for integral types, with signed and unsigned versions of each.
Yes, but the exact implementation is fairly loose. I believe the rule is "short can be no longer than long". (Slightly modified in C++11)

I was going to bring up Ada. Given its DoD roots, having to define a range of validity when declaring a variable makes sense. In the words of Bob Newhart "Men, I have just been notified that we will be surfacing in just a moment and you'll be happy to know that you will be gazing on the familiar skyline New York City..or possibly Buenos Aires"

I still think the proper place for this is in the classes, not the primitives. I also think doing this half- er...baked is not helpful. The Geant toolkit uses mm and MeV internally, and defines conversion constants so you can write energy=1.0*GeV and lenth=2.0*cm. This looks good, but length=2.0*GeV is perfectly acceptable (and is 2 meters). I would argue that should throw an error. It's not what the programmer intended.

(BTW, the Ada litany of errors? I would say "good". If the programmer's intent is ambiguous or inconsistent, the compiler should throw an error)

Is 2 degrees + 359 degrees 361 degrees? 1 degree? Something else?

Is red + green + blue black, like pigment or white, like light?

I think it's entirely reasonable to make these decisions when building classes and other data structures. I think trying to build this into intrinsic types will create more problems than it solves.
This is application defined. Different applications would need units differently.
For example adding degrees, sometimes you want the normal sum, other times just modulo 360 degrees.
Colours add differently for paint as for light, so you would need different addition rules. While still being able converting light colour to paint colour.
Etc.

FactChecker
Gold Member
Most programming languages are supposed to be kind of universal, and very few of them is so special that such extravagant functions would be addressed.
I think it is more accurate to say that most general-purpose languages are supposed to be universal. There are a great many special-purpose languages that make their targeted applications much easier to deal with. IMO, there are many more such special-purpose languages in use than there are commonly used general-purpose languages.

Jarvis323 and Rive
Summary:: For implementing lets say physical models it would be handy to not only know the numeric value of a variable, but also its units, have all kinds of conversions (fahrenheit to celcius, meters to feet, etc.) and addition/subtraction rules (can only add or subtract values with the same units).

In fact, the only programming language I know of that implements something like units is the programming language Frink.

In other programming languages, the implementation is left to the programmer, for example C++ can implement this as a class.
elcaro, you are correct that this feature should be added to more languages and is incredibly important for verification of correctness. Frankly, many of the replies in this thread are shocking and wrong. There are famous examples of systems failing because of the use of incompatible units.

F# also supports this feature very elegantly with Units of Measure.

The example at the above link illustrates how elegant this feature is.

Unit of Measure Example:
// Mass, grams.
[<Measure>] type g
// Mass, kilograms.
[<Measure>] type kg
// Weight, pounds.
[<Measure>] type lb

// Distance, meters.
[<Measure>] type m
// Distance, cm
[<Measure>] type cm

// Distance, inches.
[<Measure>] type inch
// Distance, feet
[<Measure>] type ft

// Time, seconds.
[<Measure>] type s

// Force, Newtons.
[<Measure>] type N = kg m / s^2

// Pressure, bar.
[<Measure>] type bar
// Pressure, Pascals
[<Measure>] type Pa = N / m^2

// Volume, milliliters.
[<Measure>] type ml
// Volume, liters.
[<Measure>] type L

// Define conversion constants.
let gramsPerKilogram : float<g kg^-1> = 1000.0<g/kg>
let cmPerMeter : float<cm/m> = 100.0<cm/m>
let cmPerInch : float<cm/inch> = 2.54<cm/inch>

let mlPerCubicCentimeter : float<ml/cm^3> = 1.0<ml/cm^3>
let mlPerLiter : float<ml/L> = 1000.0<ml/L>

// Define conversion functions.
let convertGramsToKilograms (x : float<g>) = x / gramsPerKilogram
let convertCentimetersToInches (x : float<cm>) = x / cmPerInch

[<Measure>] type degC // temperature, Celsius/Centigrade
[<Measure>] type degF // temperature, Fahrenheit

let convertCtoF ( temp : float<degC> ) = 9.0<degF> / 5.0<degC> * temp + 32.0<degF>
let convertFtoC ( temp: float<degF> ) = 5.0<degC> / 9.0<degF> * ( temp - 32.0<degF>)

// Define conversion functions from dimensionless floating point values.
let degreesFahrenheit temp = temp * 1.0<degF>
let degreesCelsius temp = temp * 1.0<degC>

printfn "Enter a temperature in degrees Fahrenheit."
let parsedOk, floatValue = System.Double.TryParse(input)
if parsedOk
then
printfn "That temperature in Celsius is %8.2f degrees C." ((convertFtoC (degreesFahrenheit floatValue))/(1.0<degC>))
else
printfn "Error parsing input."

The reason why this is not implemented is that technically it is very difficult to do.

elcaro and FactChecker
FactChecker
Gold Member
There are two levels of implementing units to think about in a computer language:
1) Simple conversion of units to standard units can be done in the external interfaces. That allows the programming language to be free of worrying about units.
2) Dimensional analysis like MathCad computer software by Mathsoft does (and apparently F# that @jbergman mentioned) is much more ambitious. It forbids calculations that do not have the right dimensions. You can not add x-miles to y-miles/sec. It requires the programming language, or at least the compiler, to have knowledge of the units.

Last edited:
elcaro and jbergman
PeterDonis
Mentor
2020 Award
There are famous examples of systems failing because of the use of incompatible units.
This fact does not necessarily imply that the best way to fix the problem is to build units directly into programming languages, instead of using libraries to handle units and unit conversions. The fact that not everyone agrees with your opinion on this does not mean everyone else's posts are "shocking and wrong".

Astronuc, jim mcnamara, pbuk and 1 other person