Dairy offers a type safe unit system. There are three types of units offered throughout Dairy: Distance,Angle, and Current.

Why?

  1. The type system usage means that code can be written to handle any Unit, and then get locked to that Unit’s family. This allows users to pass any Unit in the same family where a family is specified (e.g. centimeters, inches, or meters could all be used in the same place).
  2. The user is safe from accidentally using a unit from a different family once one is locked to (e.g, you can’t pass an Angle where a Distance is expected)
  3. The user can quickly convert units within the family.
  4. The user can easily define their own units of the same family for their specific use-case.
  5. Units are designed with no mutating operations, which means users never need to worry about the contents of the unit changing.

Types

Dairy comes with these units defined.

Distance

  • Linear distances.
  • Comes built in with:
    • Metric units (mm, cm, m).
    • Imperial units (in, ft).

Angle

  • Linear and wrapping angles.
  • Comes built in with:
    • Radians and degrees.
    • Wrapping (domain limits, specified here in rotations) linear (-inf, inf), wrapping [0, 0.5), and relative [-0.5, 0.5).
  • Automatically converts to linear when linear is involved on either side of the equation, otherwise, preferences the left side of the equation.

Current

  • Amperage.
  • Comes built in with:
    • Amps, Milliamps.

Units and ReifiedUnits

Dairy’s unit system is comprised of two parts. We’ll look at their full generic signature here, but we won’t worry about what it means too much for this level of documentation.

  1. Unit<U: Unit<U>>

This is like the concept of a unit, like “Meter”, “Inch”, and describes the mathematical relationship between these concepts, within the same family. Unit is an interface, which means its easy to subclass it, and implement it in enums.

We use Unit to define families of units.

i.e. Dairy has DistanceUnit and AngleUnit as families for Distance and Angle respectively.

Unit is used to define some common maths to enable conversion between different units in the same family, and makes it easy to define your own units in pre-existing families.

  1. ReifiedUnit<U: Unit<U>, RU: ReifiedUnit<U, RU>>

If Unit was our concept of a unit, then ReifiedUnit is an actual value, measured by our Unit.

This is a combination of a value, and a specific unit in a unit family.

i.e. Distance extends ReifiedUnit<DistanceUnit, Distance>

So 10 mm is a Distance! It has:

  • a value of 10
  • a unit of millimeters

ReifiedUnit is what we’ll work with most, and so the remainder of this page will look at Distance and Angle