From 0dbe3842a75345554bd1dc8857d7397170a89912 Mon Sep 17 00:00:00 2001 From: NunoSempere Date: Tue, 18 Jun 2024 20:29:55 -0400 Subject: [PATCH] start refactoring to explicitly manipulate stack struct --- README.md | 10 ++++---- fermi.go | 77 +++++++++++++++++++++++++++++++++++++++---------------- makefile | 9 ++++--- 3 files changed, 65 insertions(+), 31 deletions(-) diff --git a/README.md b/README.md index 5b9baba..e977618 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,7 @@ Sometimes, [Squiggle](https://github.com/quantified-uncertainty/squiggle), [simp Here is an example ``` -$ go run f.go +$ go run fermi.go 5000000 12000000 => 5.0M 12.0M * beta 1 200 @@ -31,7 +31,7 @@ $ go run f.go Perhaps this example is more understandable with comments and better units: ``` -$ sed -u "s|#.*||" | sed -u 's|M|000000|g' | go run f.go +$ sed -u "s|#.*||" | sed -u 's|M|000000|g' | go run fermi.go 5M 12M # number of people living in Chicago => 5.0M 12.0M * beta 1 200 # fraction of people that have a piano @@ -79,7 +79,7 @@ The difference between `=: x` and `=. y` is that `=.` clears the stack after the ``` make build sudo make install -f # rather than the previous go run f.go +f # rather than the previous go run fermi.go ``` Why use make instead of the built-in go commands? Because the point of make is to be able to share command-line recipes. @@ -93,8 +93,8 @@ sed -u "s|#.*||" | sed -u 's|M|000000|g' | f cat more/piano-tuners.f | f cat more/piano-tuners-commented.f | sed -u "s|#.*||" | sed -u 's|M|000000|g' | f -tee -a input.log | go run f.go | tee -a output.log -tee -a io.log | go run f.go | tee -a io.log +tee -a input.log | go run fermi.go | tee -a output.log +tee -a io.log | go run fermi.go | tee -a io.log function f(){ sed -u "s|#.*||" | diff --git a/fermi.go b/fermi.go index 27f5c6a..7d81ee5 100644 --- a/fermi.go +++ b/fermi.go @@ -14,7 +14,7 @@ import ( const NORMAL90CONFIDENCE = 1.6448536269514727 const GENERAL_ERR_MSG = "Valid inputs: 2 || * 2 || / 2 || 2 20 || * 2 20 || / 2 20 || clean || =: var || op var || clean || help || debug || exit" -const N_SAMPLES = 1_000_000 +const N_SAMPLES = 100_000 // Distribution interface // https://go.dev/tour/methods/9 @@ -255,6 +255,21 @@ func joinDists(old_dist Dist, new_dist Dist, op string) (Dist, error) { } /* Pretty print distributions */ +func prettyPrintInt(n int) { + switch { + case math.Abs(float64(n)) >= 1_000_000_000_000: + fmt.Printf("%dT", n/1_000_000_000_000) + case math.Abs(float64(n)) >= 1_000_000_000: + fmt.Printf("%dB", n/1_000_000_000) + case math.Abs(float64(n)) >= 1_000_000: + fmt.Printf("%dM", n/1_000_000) + case math.Abs(float64(n)) >= 1_000: + fmt.Printf("%dK", n/1_000) + default: + fmt.Printf("%df", n) + } +} + func prettyPrintFloat(f float64) { switch { case math.Abs(f) >= 1_000_000_000_000: @@ -301,8 +316,13 @@ func prettyPrintDist(dist Dist) { low := tmp_xs[low_int] high_int := N_SAMPLES * 19 / 20 high := tmp_xs[high_int] - fmt.Printf("=> samples ") - prettyPrint2Floats(low, high) + fmt.Printf("=> ") + prettyPrintFloat(low) + fmt.Printf(" ") + prettyPrintFloat(high) + fmt.Printf(" (") + prettyPrintInt(N_SAMPLES) + fmt.Printf(" samples)\n") case Beta: fmt.Printf("=> beta ") prettyPrint2Floats(v.a, v.b) @@ -316,16 +336,29 @@ func prettyPrintDist(dist Dist) { } } +/* Combine old dist and new line */ +// We want this as a function to be able to have parenthesis/recusion, possibly functions +const init_dist Scalar = Scalar(1) + +type Stack struct { + old_dist Dist + vars map[string]Dist +} + +// Could eventually be a more complex struct with: +// { Dist, VariableMaps, ConfigParams } or smth + +/* +func combineStackAndNewLine(stack Stack, new_line string) Stack { + +} +*/ + /* Main event loop */ func main() { reader := bufio.NewReader(os.Stdin) - var init_dist Dist - init_dist = Scalar(1) // Lognormal{low: 1, high: 1} - old_dist := init_dist - vars := make(map[string]Dist) - // Could eventually be a more complex struct with: - // { Dist, VariableMaps, ConfigParams } or smth + stack := Stack{old_dist: init_dist, vars: make(map[string]Dist)} EventForLoop: for { input, _ := reader.ReadString('\n') @@ -342,23 +375,23 @@ EventForLoop: fmt.Println(GENERAL_ERR_MSG) continue EventForLoop case words[0] == "debug" || words[0] == "d": - fmt.Printf("Old dist: %v\n", old_dist) - fmt.Printf("Vars: %v\n", vars) + fmt.Printf("Old dist: %v\n", stack.old_dist) + fmt.Printf("Vars: %v\n", stack.vars) continue EventForLoop case words[0] == "=:" && len(words) == 2: - vars[words[1]] = old_dist + stack.vars[words[1]] = stack.old_dist fmt.Printf("%s ", words[1]) - prettyPrintDist(old_dist) + prettyPrintDist(stack.old_dist) continue EventForLoop case words[0] == "." || words[0] == "clean" || words[0] == "c": - old_dist = init_dist + stack.old_dist = init_dist fmt.Println() continue EventForLoop case words[0] == "=." && len(words) == 2: - vars[words[1]] = old_dist + stack.vars[words[1]] = stack.old_dist fmt.Printf("%s ", words[1]) - prettyPrintDist(old_dist) - old_dist = init_dist + prettyPrintDist(stack.old_dist) + stack.old_dist = init_dist fmt.Println() continue EventForLoop // Other possible cases: @@ -370,19 +403,19 @@ EventForLoop: } } - op, new_dist, err := parseLine(input, vars) + op, new_dist, err := parseLine(input, stack.vars) if err != nil { continue EventForLoop } - joint_dist, err := joinDists(old_dist, new_dist, op) + joint_dist, err := joinDists(stack.old_dist, new_dist, op) if err != nil { fmt.Printf("%v\n", err) fmt.Printf("Dist on stack: ") - prettyPrintDist(old_dist) + prettyPrintDist(stack.old_dist) continue EventForLoop } - old_dist = joint_dist - prettyPrintDist(old_dist) + stack.old_dist = joint_dist + prettyPrintDist(stack.old_dist) } } diff --git a/makefile b/makefile index 211d012..0a23053 100644 --- a/makefile +++ b/makefile @@ -1,8 +1,9 @@ run: - go run f.go + go run fermi.go build: - go build f.go + go build fermi.go -install: f - sudo mv f /usr/bin/f +install: fermi + sudo mv fermi /usr/bin/fermi + sudo ln -s /usr/bin/fermi /usr/bin/f