2

I need to design a function to perform the basic arithmetic operations that are addition (+), subtraction (-), multiplication (x), and division (/) between 2 numbers.

That function takes 3 arguments:
-number1: composed of a value and a unit.
-number2: compoased of a value and a unit.
-operation_type: one of the 4 aforementioned operations.

and should return:
-number3: composed of a value and a unit.

Returning number3's value is easy as all I need to do is use conditional statements to perform the corresponding operation (e.g. if (operation_type == 'addition') { number3.value = number1.value + number2.value; } ).

However I'm having difficulties figuring out how I should represent and deal with the unit (for multiplication and subtraction operations, as for addition and subtraction it remains the same) in a way that I can chain up multiple operations and properly update the resulting unit every time. Here is an example:

operations type: multiplications
number1.unit: Kw
number2.unit: h / user / year
number3.unit: Kwh / user / year  _
                                  |
number1.unit: Kwh / user / year  <-
number2.unit: user
number3.unit: Kwh / year  _
                           |
number1.unit: Kwh / year  <-
number2.unit: year
number3.unit: Kwh
...

My only constraint is that the unit must initially be represented as a string because it is stored in the database, then we can parse parse it into an object/array as needed.

Some of the problems I'm facing:
Q1: how to ensure consistent order in the resulting unit (e.g. h x Kw and Kw x h should both give Kwh)?
Q2: how to deal with complex units (e.g. foo / Kw x h / bar)?

And because hope dies last:
Q3: Are there any known algorithms / design patterns for dealing with this?

2 Answers 2

4

If you just need to deal with physical quantities, then you can choose an n-dimensional system of physical units (length, mass, time, charge, etc.) that fits your domain. Any physical unit is a product of powers of the fundamental units (positive and negative): e.g. force = mass * length * time^-2. When you multiply physical quantities, you can just add the powers of the fundamental units. If you need to handle fractional powers, I would represent them as ratios (1/3), not floating point (0.33333333)

Ordering for human display is largely a matter of custom. Typically the order is positive powers of mass, length, time in the numerator and denominator, e.g. km-m^2/sec^2. But there are many exceptions. For example, Hubble's constant has dimension time^-1, but it is typically expressed as velocity / distance, e.g. km/sec / megaparsec.

As far as I know, C++ is the only popular language with a type system powerful enough to conveniently verify physical unit balance at compile time. There are several C++ libraries available, including one in Boost. If you are not using C++, you may want to look at one of them for inspiration.

2
  • F# has units of measure out of the box, Haskell can support them pretty easily as a library, I assume these don't count as popular ;)
    – jk.
    Aug 20, 2012 at 17:44
  • 1
    @jk: As far as I know evidently wasn't very far. I wouldn't call Haskell popular; not sure about F#. Aug 20, 2012 at 23:38
1

I would just create a lookup table.

It's the fastest way to guarantee that when you get kW and h, regardless of order, that you'll come back with kW*h.

The only downside is if you have a very large number of combinations then it can be a pain to put the table together.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.