## Temperature conversion

In this worked example, we look at temperature conversion between Celsius, Kelvin and Fahrenheit. In our last example we mentioned the star ket |*>, which defines an operator with respect to all kets. Well, this time we have a variant of the star ket, one where we also specify a "category". So |K: *> is used to define an operator with respect to only kets that have the category "K". Likewise |C: *> defines an operator with respect to all kets with the category "C". Where we are using K as the category for Kelvin temperatures, C for Celsius temperatures, and F for Fahrenheit temperatures. Next feature we need to describe is the #=> learn rule. This learn rule has the property that the RHS is only calculated at invoke time, not at definition time, as is the case with the standard learn rule =>. And unlike the memoizing learn rule !=> we don't store the results of the computation. Next, we have __ which is an infix operator that concatenates the labels of the given pair of kets, with a single space char between them. In contrast to the _ infix operator that concatenates the labels without a space char between the labels. Eg:

sa: |string1> __ |string2> |string1 string2> sa: |string1> _ |string2> |string1string2>

round[n] rounds the value in the ket label to n decimal places. minus[n] subtracts n from the ket label it is applied to. plus[n] adds n to the given ket. extract-value removes the category from the given ket. And times-by[n] multiplies by n. And that is all we need to define our temperature conversion operators. Using the star ket and the stored-rule learn rule, we also provide some alias's. So the to-K operator just invokes the to-Kelvin operator, and so on for to-C and to-F.

Here is the code:

-- Convert between Kelvin, Celsius and Fahrenheit: to-Kelvin |K: *> #=> |_self> to-Celsius |K: *> #=> |C:> __ round[2] minus[273.15] extract-value |_self> to-Fahrenheit |K: *> #=> |F:> __ round[2] minus[459.67] times-by[9/5] extract-value |_self> to-Kelvin |C: *> #=> |K:> __ round[2] plus[273.15] extract-value |_self> to-Celsius |C: *> #=> |_self> to-Fahrenheit |C: *> #=> |F:> __ round[2] plus[32] times-by[9/5] extract-value |_self> to-Kelvin |F: *> #=> |K:> __ round[2] times-by[5/9] plus[459.67] extract-value |_self> to-Celsius |F: *> #=> |C:> __ round[2] times-by[5/9] minus[32] extract-value |_self> to-Fahrenheit |F: *> #=> |_self> to-K |*> #=> to-Kelvin |_self> to-C |*> #=> to-Celsius |_self> to-F |*> #=> to-Fahrenheit |_self> table[Celsius, to-Kelvin, to-Fahrenheit] range(|C: 0>, |C: 100>, |5>)

Here is the output from the code:

+---------+-----------+---------------+ | Celsius | to-Kelvin | to-Fahrenheit | +---------+-----------+---------------+ | C: 0 | K: 273.15 | F: 32 | | C: 5 | K: 278.15 | F: 41 | | C: 10 | K: 283.15 | F: 50 | | C: 15 | K: 288.15 | F: 59 | | C: 20 | K: 293.15 | F: 68 | | C: 25 | K: 298.15 | F: 77 | | C: 30 | K: 303.15 | F: 86 | | C: 35 | K: 308.15 | F: 95 | | C: 40 | K: 313.15 | F: 104 | | C: 45 | K: 318.15 | F: 113 | | C: 50 | K: 323.15 | F: 122 | | C: 55 | K: 328.15 | F: 131 | | C: 60 | K: 333.15 | F: 140 | | C: 65 | K: 338.15 | F: 149 | | C: 70 | K: 343.15 | F: 158 | | C: 75 | K: 348.15 | F: 167 | | C: 80 | K: 353.15 | F: 176 | | C: 85 | K: 358.15 | F: 185 | | C: 90 | K: 363.15 | F: 194 | | C: 95 | K: 368.15 | F: 203 | | C: 100 | K: 373.15 | F: 212 | +---------+-----------+---------------+ |table>

Raw file here.