about summary refs log tree commit diff
path: root/tools/seqstat/sequence.go
diff options
context:
space:
mode:
authorFranck Cuny <franck@fcuny.net>2022-06-19 15:11:59 -0700
committerFranck Cuny <franck@fcuny.net>2022-06-19 15:17:50 -0700
commitc4c1b7af140c1dd99c7b0520178eea02edd63e2b (patch)
treead5a5a0244b921d09cfedbd72be758a0c5f9e867 /tools/seqstat/sequence.go
parentfeat(tools/numap): add a tool to report NUMA topology of a host (diff)
downloadworld-c4c1b7af140c1dd99c7b0520178eea02edd63e2b.tar.gz
feat(tools/seqstat): add a tool to report stats about a sequence
For example:
```
% echo 1 20 12 32 19 2 | ./seqstat -S
▁▅▃█▅▁
min:   1.000000
max:   32.000000
avg:   14.333333
p50:   19.000000
p90:   32.000000
p99:   32.000000
p999:  32.000000
ordered sequence: [1 2 12 19 20 32]
```

Change-Id: I9303bd7d0e964948143e77c868de8777cd7a9951
Reviewed-on: https://cl.fcuny.net/c/world/+/454
Tested-by: CI
Reviewed-by: Franck Cuny <franck@fcuny.net>
Diffstat (limited to '')
-rw-r--r--tools/seqstat/sequence.go79
1 files changed, 79 insertions, 0 deletions
diff --git a/tools/seqstat/sequence.go b/tools/seqstat/sequence.go
new file mode 100644
index 0000000..d4ec91b
--- /dev/null
+++ b/tools/seqstat/sequence.go
@@ -0,0 +1,79 @@
+package main
+
+import (
+	"sort"
+)
+
+var (
+	ticks = []rune{'\u2581', '\u2582', '\u2583', '\u2584', '\u2585', '\u2586', '\u2587', '\u2588'}
+)
+
+type sequence struct {
+	elements       []float64
+	elementsSorted []float64
+	min            float64
+	max            float64
+	factor         int
+	sum            float64
+}
+
+func (s *sequence) avg() float64 {
+	return s.sum / float64(len(s.elements))
+}
+
+func (s *sequence) p50() float64 {
+	return s.elementsSorted[len(s.elementsSorted)*50/100]
+}
+
+func (s *sequence) p90() float64 {
+	return s.elementsSorted[len(s.elementsSorted)*90/100]
+}
+
+func (s *sequence) p99() float64 {
+	return s.elementsSorted[len(s.elementsSorted)*99/100]
+}
+
+func (s *sequence) p999() float64 {
+	return s.elementsSorted[len(s.elementsSorted)*999/1000]
+}
+func (s *sequence) histogram() []rune {
+	histogram := make([]rune, len(s.elements))
+	for i, num := range s.elements {
+		v := (((int(num) - int(s.min)) << 8) / s.factor)
+		histogram[i] = ticks[v]
+	}
+	return histogram
+}
+
+func newSequence(elements []float64) *sequence {
+	s := new(sequence)
+	s.elements = elements
+
+	s.min = s.elements[0]
+	s.max = s.elements[0]
+
+	s.sum = 0
+
+	for _, element := range s.elements {
+		if element > s.max {
+			s.max = element
+		}
+		if element < s.min {
+			s.min = element
+		}
+		s.sum += element
+	}
+
+	s.factor = ((int(s.max) - int(s.min)) << 8) / (len(ticks) - 1)
+
+	if s.factor < 1 {
+		s.factor = 1
+	}
+
+	elementsSorted := make([]float64, len(elements))
+	copy(elementsSorted, elements)
+	sort.Float64s(elementsSorted)
+	s.elementsSorted = elementsSorted
+
+	return s
+}