I'm trying to use protocols to create an engineering number type (a "knumber"), so I can say (+ "1k" "2Meg") and get something like "2.001Meg". I should be able to get the floating point value from the knumber like so (:val my-knumber), but normally the printer should display the string, which is also accessible like so (:string my-knumber). This number will support all the usual p, n, u, m, k, Meg, G suffixes, and convert as required among them, such as (/ "1Meg" "1G") -> "1m"). I want to be able to pass this to any function which expects a number.
Anyway, Can someone suggest a strategy for this? I think I need to use protocols. I currently have a (defrecord knumber [val string]) but I'm not sure what's next.
What protocols do clojure numbers satsify? I'm thinking I need to extend some existing protocols/interfaces for this.
Thanks
I think your strategy should probably be as follows:
KNumber as something like (defrecord knumber [value unit-map]) unit-map a map of units to integer exponents (you are going to want units like m/s^2 if these are engineering numbers, right?). It might look something like {"m" 1 "s" -2}, KNumber implement java.lang.Number so that you can use it with other mathematical functions that already exist in Clojure. You'll need to implement doubleValue, longValue etc.NumberWithUnits that you can extend to both KNumbers and normal clojure numbers. At a minimum it should have methods (numeric-value [number]) and (get-units [number])
+, *, - etc. in your own namespace that operate on anything that implements the NumberWithUnits protocol and return a KNumber. If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With