Posted to tcl by kbk at Fri Jul 04 17:18:54 GMT 2008view pretty
namespace path {::tcl::mathop ::tcl::mathfunc} # Take a decimal number and convert it to a rational. Return a two # element list of numerator and denominator proc to-rational {n} { if {![regexp {^([-+]?[0-9]*)(?:[.]([0-9]*))?$} $n -> integer fraction]} { return -code error "$n is not a number" } set denom [** 10 [string length $fraction]] # TODO - Reduce to lowest terms return [list $integer$fraction $denom] } puts [to-rational 6.25] # Take a decimal number representing a percentage and convert it to a # rational. Return a two element list of numerator and denominator proc percent {n} { lassign [to-rational $n] num denom # TODO - Reduce to lowest terms return [list $num [* 100 $denom]] } puts [percent 6.25] # Multiply two rationals proc rat-times {m n} { set result {} foreach x $m y $n { lappend result [* $x $y] } return $result } # What is 6.25% of 19.45? set val [rat-times [percent 6.25] [to-rational 19.45]] puts $val # Take the integer part of a rational, with banker's rounding proc rat-int {n} { lassign $n num denom set ipart [/ $num $denom] set fpart [% $num $denom] if {$fpart < 0} { incr ipart -1 incr fpart $denom } if {2 * $fpart < $denom} { return $ipart } elseif {2 * $fpart > $denom} { return [+ $ipart 1] } else { return [+ $ipart [% $ipart 2]] } } # How many pennies is 6.25% times 19.45? set resultCents [rat-int [rat-times {100 1} $val]] puts $resultCents # Convert an integer count of pennies to standard notation proc penniesToDollars {cents} { # TODO - Doesn't handle + and - signs correctly if {[string length $cents] < 3} { set cents [string repeat [- 3 [string length $cents]] 0]$cents } return [string range $cents 0 end-2].[string range $cents end-1 end] } puts \$[penniesToDollars $resultCents]