Search Apps Documentation Source Content File Folder Download Copy Actions Download State String Boolean Number Struct Map Slice Pointer Function Closure Reference Nil Package Type Interface Unknown

bidimapdemo.gno

2.73 Kb · 72 lines
 1// Package bidimapdemo is a small gnoweb demo of the bidirectional map provided
 2// by the [p/moul/x/daily/bidimap](/p/moul/x/daily/bidimap/v0) library: it shows
 3// the reverse lookup and what happens when a binding is displaced.
 4//
 5// It contains no map logic of its own. Stateless, so Render is deterministic —
 6// which is precisely what the library is for.
 7package bidimapdemo
 8
 9import (
10	"strconv"
11	"strings"
12
13	"gno.land/p/moul/x/daily/bidimap/v0"
14)
15
16// Render renders the demo for gnoweb.
17func Render(path string) string {
18	var b strings.Builder
19	b.WriteString("# Bidirectional Map\n\n")
20	b.WriteString("Unique in both directions, demoing the ")
21	b.WriteString("[`p/moul/x/daily/bidimap`](/p/moul/x/daily/bidimap/v0) library.\n\n")
22
23	m := bidimap.New()
24	m.Put("alice", "admin")
25	m.Put("bob", "auditor")
26	m.Put("carol", "treasurer")
27
28	b.WriteString("## Roles\n\n")
29	b.WriteString(table(m))
30
31	b.WriteString("\n## Both directions are O(1)\n\n")
32	v, _ := m.Get("bob")
33	k, _ := m.GetKey("treasurer")
34	b.WriteString("- `Get(\"bob\")` → `" + v + "`\n")
35	b.WriteString("- `GetKey(\"treasurer\")` → `" + k + "` — the reverse index, not a scan\n\n")
36
37	b.WriteString("## Displacing a binding\n\n")
38	b.WriteString("Both sides are unique, so giving `alice` the `auditor` role cannot ")
39	b.WriteString("simply be written — `bob` already holds it, and `alice` already holds ")
40	b.WriteString("`admin`. `Put` **replaces**, and reports what it displaced:\n\n")
41	evicted, _ := m.Put("alice", "auditor")
42	b.WriteString("| displaced key | displaced value |\n|---|---|\n")
43	for _, p := range evicted {
44		b.WriteString("| `" + p[0] + "` | `" + p[1] + "` |\n")
45	}
46	b.WriteString("\n" + table(m))
47	b.WriteString("\n`bob` is now unassigned and the `admin` role is vacant — one call, ")
48	b.WriteString("both indexes still agreeing.\n\n")
49
50	b.WriteString("## Refusing instead\n\n")
51	b.WriteString("`PutUnique` makes the other choice: it declines rather than displace.\n\n")
52	ok := m.PutUnique("dave", "auditor")
53	b.WriteString("- `PutUnique(\"dave\", \"auditor\")` → `" + strconv.FormatBool(ok) + "` — the role is taken\n")
54	ok = m.PutUnique("dave", "secretary")
55	b.WriteString("- `PutUnique(\"dave\", \"secretary\")` → `" + strconv.FormatBool(ok) + "` — both sides free\n\n")
56	b.WriteString(table(m))
57
58	b.WriteString("\n> Keys come back **sorted**, never in map order: gno map iteration ")
59	b.WriteString("order is unspecified, and a page built from one can differ between ")
60	b.WriteString("nodes — a consensus bug, not a cosmetic one.\n")
61	return b.String()
62}
63
64func table(m *bidimap.BiMap) string {
65	var b strings.Builder
66	b.WriteString("| person | role |\n|---|---|\n")
67	m.Iterate(func(k, v string) bool {
68		b.WriteString("| `" + k + "` | `" + v + "` |\n")
69		return false
70	})
71	return b.String()
72}