diff options
Diffstat (limited to 'src/net/http/mapping_test.go')
-rw-r--r-- | src/net/http/mapping_test.go | 154 |
1 files changed, 154 insertions, 0 deletions
diff --git a/src/net/http/mapping_test.go b/src/net/http/mapping_test.go new file mode 100644 index 0000000..0aed9d9 --- /dev/null +++ b/src/net/http/mapping_test.go @@ -0,0 +1,154 @@ +// Copyright 2023 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package http + +import ( + "cmp" + "fmt" + "slices" + "strconv" + "testing" +) + +func TestMapping(t *testing.T) { + var m mapping[int, string] + for i := 0; i < maxSlice; i++ { + m.add(i, strconv.Itoa(i)) + } + if m.m != nil { + t.Fatal("m.m != nil") + } + for i := 0; i < maxSlice; i++ { + g, _ := m.find(i) + w := strconv.Itoa(i) + if g != w { + t.Fatalf("%d: got %s, want %s", i, g, w) + } + } + m.add(4, "4") + if m.s != nil { + t.Fatal("m.s != nil") + } + if m.m == nil { + t.Fatal("m.m == nil") + } + g, _ := m.find(4) + if w := "4"; g != w { + t.Fatalf("got %s, want %s", g, w) + } +} + +func TestMappingEachPair(t *testing.T) { + var m mapping[int, string] + var want []entry[int, string] + for i := 0; i < maxSlice*2; i++ { + v := strconv.Itoa(i) + m.add(i, v) + want = append(want, entry[int, string]{i, v}) + + } + + var got []entry[int, string] + m.eachPair(func(k int, v string) bool { + got = append(got, entry[int, string]{k, v}) + return true + }) + slices.SortFunc(got, func(e1, e2 entry[int, string]) int { + return cmp.Compare(e1.key, e2.key) + }) + if !slices.Equal(got, want) { + t.Errorf("got %v, want %v", got, want) + } +} + +func BenchmarkFindChild(b *testing.B) { + key := "articles" + children := []string{ + "*", + "cmd.html", + "code.html", + "contrib.html", + "contribute.html", + "debugging_with_gdb.html", + "docs.html", + "effective_go.html", + "files.log", + "gccgo_contribute.html", + "gccgo_install.html", + "go-logo-black.png", + "go-logo-blue.png", + "go-logo-white.png", + "go1.1.html", + "go1.2.html", + "go1.html", + "go1compat.html", + "go_faq.html", + "go_mem.html", + "go_spec.html", + "help.html", + "ie.css", + "install-source.html", + "install.html", + "logo-153x55.png", + "Makefile", + "root.html", + "share.png", + "sieve.gif", + "tos.html", + "articles", + } + if len(children) != 32 { + panic("bad len") + } + for _, n := range []int{2, 4, 8, 16, 32} { + list := children[:n] + b.Run(fmt.Sprintf("n=%d", n), func(b *testing.B) { + + b.Run("rep=linear", func(b *testing.B) { + var entries []entry[string, any] + for _, c := range list { + entries = append(entries, entry[string, any]{c, nil}) + } + b.ResetTimer() + for i := 0; i < b.N; i++ { + findChildLinear(key, entries) + } + }) + b.Run("rep=map", func(b *testing.B) { + m := map[string]any{} + for _, c := range list { + m[c] = nil + } + var x any + b.ResetTimer() + for i := 0; i < b.N; i++ { + x = m[key] + } + _ = x + }) + b.Run(fmt.Sprintf("rep=hybrid%d", maxSlice), func(b *testing.B) { + var h mapping[string, any] + for _, c := range list { + h.add(c, nil) + } + var x any + b.ResetTimer() + for i := 0; i < b.N; i++ { + x, _ = h.find(key) + } + _ = x + }) + }) + } +} + +func findChildLinear(key string, entries []entry[string, any]) any { + for _, e := range entries { + if key == e.key { + return e.value + } + } + return nil +} |