-
-
Notifications
You must be signed in to change notification settings - Fork 15
The conversion algorithm
I imagined the conversion task as a tree: there is a root node that can be the main unit of a certain property (e.g. the meter for the length property). The meter node is connected to centimeters node, kilometers node, etc. The connection between two units are represented by some values:
- A product coefficient:
coefficientProduct
- A sum coefficient:
coefficientSum
- A conversion type:
conversionType
Let's go in depth. Let x
be the known value of the child node (e.g. x
= 1 centimeter) and y
the converted value from the child node, i.e. the value of the parent node (e.g. y
are meters). If we want to convert 1 centimeter to meters, we have to multiply x
=1 by 0.01. In general a linearConversion
is in the form: y=ax+b
. In this example a=0.01
and b=0
. On the other hand a reciprocalConversion
is expressed like: y=(1/a)*x+b
, and so on and so forth.
Why a conversion tree? Because it is the natural way we express the conversions: we say that a foot is 12 inch and not a foot is 0.3048 meters.
Here's an example of a conversion tree:
- Meters
- Centimeters
- Inch
- Feet
- Inch
- Nautical miles
- Yards
- Miles
- ...
- Centimeters
In the code this tree is almost the same:
Node(name: LENGTH.meters, leafNodes: [
Node(coefficientProduct: 0.01, name: LENGTH.centimeters, leafNodes: [
Node(coefficientProduct: 2.54, name: LENGTH.inches, leafNodes: [
Node(
coefficientProduct: 12.0,
name: LENGTH.feet,
),
Node(
coefficientProduct: 1e-3,
name: LENGTH.mils,
),
]),
]),
Node(
coefficientProduct: 1852.0,
name: LENGTH.nauticalMiles,
),
Node(coefficientProduct: 0.9144, name: LENGTH.yards, leafNodes: [
Node(
coefficientProduct: 1760.0,
name: LENGTH.miles,
),
]),
//...
])