A calculator for uncertain quantities using Ocaml
Sun Nov 12 10:36:43 EST 2006
Error propagation is an important tool for measuring the uncertainty
of a final result based on the uncertainties of the underlying
measurements. It is also the bane of many first year science
students' lives. A calculator that
worked with uncertain quantities and did the error propagation
automatically would be a useful tool, eg
22.0,5.0% + 10.0,1.0 to add 22
with an uncertainty of 5% to 10 with an uncertainty of 1.
Here I show how to accomplish this using Ocaml. Ocaml is a good choice for this task because the program can be broken down easily into its independent sub-tasks using the language facilities:
- use the module system to define an UncertainNumber abstract datatype, with addition, subtraction, multiplication and division operations defined for this datatype.
- use ocamllex and ocamlyacc to construct a calculator that deals with this datatype.
The second task has already been done in SooHyoung Oh's Ocamlyacc tutorial, at least the hard bits about defining the parser. Fairly simple modifications are required to deal with the new number type.
The first task involves dealing with the intricacies of the Ocaml module system, as I have been describing in my previous few blog entries. The basic method is to create two abstract datatypes, one to represent the UncertainNumber type and the other to deal with the AlgebraicNumber datatype for which the addition etc operators are defined. This allows the extension of the calculator to other datatypes such as ComplexNumbers or Vectors by redefining the construction and accessor functions in the underlying representation and the algebraic functions in the AlgebraicNumber datatype. From the point of view of the parser the only functions that it is concerned with is AlgebraicNumber.add etc.
The third task is to tie the newly defined abstract datatype to the parser. This bit is a tad inelegant as I cannot just use the nums.ml file directly. Instead I have to extract the signature definitions into separate Uncert.mli and AlgNum.mli files (without the module and end lines) and the implementations (ie the struct definitions) into Uncert.ml and AlgNum.ml (changing the elt type of AlgNum to Uncert.t).
A longer descripting containing full source code is in the Ocaml section of my website under the Code main branch. The [source code for uncertainty calculator] is available from this link.
This is of course only the very basic model of the calculator. Obvious extensions for this datatype would be definition of functions with associated error propagation functions. Extension of the calculator as a whole could be along the lines of making it easier to add new modes to the calculator ie operations on different datatypes. Further investigation into the workings of functors is probably required to get this to work, as it would be nice to be able to add new functionality at run time (ie define new functions and modes from a configuration file).