Examples
How it works: values and units
A quantity consists of two parts: a value and a unit. Internally, a unit is represented by a list of seven integers, one for each SI base unit:
unit: list[int] # [meter, kilogram, second, ampere, mol, kelvin, candela]
Each value in this list corresponds to the exponent of the respective unit.
While it is possible to construct a SIObject by providing a value and a unit,
it is not recommendend because it is not very readable and prone to error:
1 2 3 | |
125 kg
Instead, we can use one of the "units" (a SIObject with value one)
defined in the package and multiply it by the value.
Here we use KILOGRAM to yield the same result as above:
1 2 3 | |
125 kg
For convenience and readability, si_units also defines prefixes.
The following again yields the same result using the KILO
prefix together with GRAM:
1 2 3 | |
125 kg
Prefixes and units can be used to define new types that you may want to reuse across your code:
1 2 3 4 5 | |
Unit conversion
Consider the pressure of an ideal gas:
1 2 3 4 5 6 | |
123.94785148011941 kPa
Internally, all SIObjects are represented in base SI units.
Dividing by a unit (including prefixes) yields the value which can be a
scalar or an array or tensor. This can be used to "convert" a quantity
into a value of the desired unit:
1 2 3 4 5 6 7 8 | |
pressure / bar: 1.2394785148011942
pressure / mN/A^2: 1.239478514801194e-12
volume / l: 1500.0
One-dimensional array constructors
There are several ways to construct a SIObject where the value
is a one-dimensional array.
1 2 3 4 5 6 7 | |
For multi-dimensional arrays, first construct a numpy.ndarray of the
desired shape and multiply it by an unit.
Gravitational pull of the moon on the earth
1 2 3 4 5 6 | |
1.992075748302325e26 N
Pressure distribution in the atmosphere
Using the barometric formula.
This example demonstrates how dimensioned arrays can be constructed
using numpy.ndarrays.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | |
z = 1.0000000000 p = 99.9879378249
z = 7778.6666666667 p = 39.1279560236
z = 15556.3333333333 p = 15.3118163640
z = 23334.0000000000 p = 5.9919235296
z = 31111.6666666667 p = 2.3448000375
z = 38889.3333333333 p = 0.9175830080
z = 46667.0000000000 p = 0.3590747881
z = 54444.6666666667 p = 0.1405155744
z = 62222.3333333333 p = 0.0549875048
z = 70000.0000000000 p = 0.0215180823
Alternatively, we could have used si_units.linspace instead of numpy:
1 2 3 4 5 | |
Using numpy or torch functions
A SIObject wraps a provided Python object, allowing you to use numpy arrays, torch tensors,
or jax arrays as the underlying data type.
Binary operations work between objects with compatible inner types and units.
The sqrt and cbrt methods are supported when the unit exponents are divisible accordingly.
This works for scalars:
1 2 3 4 5 6 | |
1 m
1 m
torch.tensor's work as well:
1 2 3 4 5 6 | |
tensor([ 4., 9., 16.]) m²
tensor([2., 3., 4.]) m
For unsupported operations, you can retrieve the underlying Python object by dividing the
SIObject by its unit, then perform the operation directly on the raw data.