
"Beth Jacobson" wrote [...]
Under/overflow will certainly be an issue for some people if they can't specify their own base units, but I don't know if a tight coupling between units and dimensions is the best solution. Could there be some sort of global setting (a facet, maybe?) where we could specify units for base dimensions for the entire application?
The quantity containers and unit typedefs can be easily customised by the user to whatever they prefer: namespace my{ typedef boost::pqs::length::mm distance; typedef boost::pqs::time::s time; typedef boost::pqs::velocity::mm_div_s velocity; } void f() { my:::velocity v = my::distance(1) / my_time(1); } [...]
Another example would be something like this (excuse the psuedo-pqs):
No problem..... ;-)
pqs::pressure::psi WaterPressure(pqs::length::feet depth) { const pqs::length_per_pressure::foot_per_psi pressureRatio(2.31); return depth/pressureRatio; }
If units weren't specified in the function declaration, it could be called with the wrong ones, and its return value would be garbage.
Both your example and mine have a common element though. They both involve moving between numeric values and dimensions. I can't think of an instance where units would be useful when that isn't the case. If that's true, then it seems like overkill to require bound units throughout the program. A simpler solution would be to prohibit dimension variables from being assigned or returning "raw" numbers. The only way to get or set a value would be through unit functions like this.
PQS quantities can't be converted to raw numbers. double val = pqs::length::m(1) ;// Error but a function is provided to get the numeric_value: double val = pqs::length::m(1).numeric_value() ;// Ok Its name is quite long so it's easy to spot in code.
pqs::energy energyVal = pqs::kcal(value);
My water pressure example would look like this
pqs::pressure WaterPressure(pqs::length depth) { const pqs::length_per_pressure ratio(pqs::foot_per_psi(2.31)); return depth/ratio; }
The value, 2.31, would be converted to the global units, whatever they happened to be, so the function would work with any unit system. Since units would be specified at the point of conversion, this method might even be a little safer. In pqs, you might do something like this
pqs::length::m depth;
// lots of code
Its not possible to initialise a double from a quantity in PQS:
double depthAsDouble(depth);
so the the above will not compile.
SetFieldValue("DepthInFt", depthAsDouble);
cout << "Enter new depth (in feet): " cin >> depth;
Because depth is declared far from where it's output and reassigned, these mistakes would be easy to miss.
Not so for the above reason! In PQS the units are part of the type. IOW the numeric value and its unit are always tightly coupled in code. That is a powerful feature. Once the numeric part of a quantity is disassociated from its unit then manual checking and external documentation is required, which is often the current situation wherever doubles are used to represent quantities. Manual checking doesnt always work as well as intended... That of course is why the Mars lander crashed! regards Andy Little