Need help with units library

alexander1974 via Digitalmars-d-learn digitalmars-d-learn at puremagic.com
Fri Aug 18 06:21:06 PDT 2017


I want to write a library for working with units (lengths, 
weights, ...). It should allow maths and converting with/between 
different units (cm to mm, angstrom to meter, ...).

The SI Sytem consists of the base units for length (meter), mass 
(kg), time (second) ,... and the prefixes like yotta (10²⁴) to 
femto (10⁻¹⁵).

enum for the prefixes

enum prefix {
   ...
   c = -2, /// for centi
   m = -3, /// for mili
   ...
}

enum for different units

enum unit { length, weight, ... }

I take a struct to define the units

struct units (T) {
   T _value;     /// the value (eg 10)
   prefix _pre;  /// the SI-prefix (eg. c for cm)
   unit _unit;   /// the unit like length or weight to keep them 
apart
};

to keep it simple maybe functions could help (also with ifti)

auto cm (T) (T value) { return units!T(value, prefix.c, 
unit.length); }

conversion within a unit is simple comparing the prefixes:

real conv (prefix lhs, prefix rhs) {
   import std.math:pow;
   int c = rhs - lhs;
   return pow(10.0,c);
}

math could be done with opBinary overloading in the struct

auto opBinary(string op)(length rhs)
   {
     return mixin("units(_value "~op~" 
rhs._value*conv(pre,rhs.pre),_pre, _unit)");
   }
auto opBinary(string op)(T rhs) if (isNumeric!T)
   {
     return mixin("units(_value "~op~" rhs,_pre,_unit)");
   }

What do you think about the layout so far?
Is there a better way?

How to implement non-SI-units?


More information about the Digitalmars-d-learn mailing list