detached 150eab2

docs(readme): add benchmark table pinned to v0.1.0

commit
150eab2bf50164476a974b187a695f92a83ed61b
author
brice · · 2026-10-10 06:10 UTC
parent
3b1b6ef
signature
GPG VerifiedCD88F9E564E0102646FB6077A1A07C7C7C3E349D · arch-gpg Verified for the committer email
1 file · +23 -1
M README.md +23 -1
@@ -21,7 +21,8 @@ output.DP-1.scale = 1.5
2121 - **Safe for real configs**: atomic saves, symlinked dotfiles, editors that
2222 save by rename, missing directories, broken files that keep the last good
2323 config, and warnings that never print values (they may be secrets).
24-- **Fast**: about 800 MB/s to parse, a few allocations per reported change.
24+- **Fast**: about 750 MB/s to parse, 2 allocations per reported change
25+ (see [Performance](#performance)).
2526
2627 ```sh
2728 go get github.com/bnema/kvconf
@@ -107,6 +108,27 @@ skips saves that change no value.
107108 - `WriteFile`: atomic replace, written through symlinks.
108109 - `ReadFile`: bounded read that rejects FIFOs and devices without blocking.
109110
111+## Performance
112+
113+Measured at `v0.1.0` (`3b1b6ef`, 2026-10-10) with Go 1.27.1 on linux/amd64
114+with an AMD Ryzen 9 7900X3D. Values are medians of 6 runs. The input is a
115+realistic ~2.9 KB config of 100 lines with comments, 60 binds and 8 outputs.
116+
117+| Benchmark | Time/op | Throughput | Bytes/op | Allocs/op |
118+|---|---:|---:|---:|---:|
119+| `Parse` (file to entries) | 3.9 µs | 755 MB/s | 10.4 KiB | 5 |
120+| `Unmarshal` (file to struct, maps included) | 12.5 µs | 232 MB/s | 21.7 KiB | 47 |
121+| `Decode` (5 scalar entries) | 177 ns | | 112 B | 1 |
122+| `Marshal` (struct to file) | 11.6 µs | | 15.5 KiB | 19 |
123+| `Set` (edit one key in place) | 2.4 µs | | 10.5 KiB | 5 |
124+| `Watch` (one write to one report, inotify) | 5.5 µs | | 256 B | 2 |
125+
126+Reproduce with:
127+
128+```sh
129+go test -run '^$' -bench . -benchmem -count 6 .
130+```
131+
110132 ## License
111133
112134 MIT
@@ -21,7 +21,8 @@ output.DP-1.scale = 1.5
21 - **Safe for real configs**: atomic saves, symlinked dotfiles, editors that21 - **Safe for real configs**: atomic saves, symlinked dotfiles, editors that
22 save by rename, missing directories, broken files that keep the last good22 save by rename, missing directories, broken files that keep the last good
23 config, and warnings that never print values (they may be secrets).23 config, and warnings that never print values (they may be secrets).
24-- **Fast**: about 800 MB/s to parse, a few allocations per reported change.24+- **Fast**: about 750 MB/s to parse, 2 allocations per reported change
25+ (see [Performance](#performance)).
25 26
26 ```sh27 ```sh
27 go get github.com/bnema/kvconf28 go get github.com/bnema/kvconf
@@ -107,6 +108,27 @@ skips saves that change no value.
107 - `WriteFile`: atomic replace, written through symlinks.108 - `WriteFile`: atomic replace, written through symlinks.
108 - `ReadFile`: bounded read that rejects FIFOs and devices without blocking.109 - `ReadFile`: bounded read that rejects FIFOs and devices without blocking.
109 110
111+## Performance
112+
113+Measured at `v0.1.0` (`3b1b6ef`, 2026-10-10) with Go 1.27.1 on linux/amd64
114+with an AMD Ryzen 9 7900X3D. Values are medians of 6 runs. The input is a
115+realistic ~2.9 KB config of 100 lines with comments, 60 binds and 8 outputs.
116+
117+| Benchmark | Time/op | Throughput | Bytes/op | Allocs/op |
118+|---|---:|---:|---:|---:|
119+| `Parse` (file to entries) | 3.9 µs | 755 MB/s | 10.4 KiB | 5 |
120+| `Unmarshal` (file to struct, maps included) | 12.5 µs | 232 MB/s | 21.7 KiB | 47 |
121+| `Decode` (5 scalar entries) | 177 ns | | 112 B | 1 |
122+| `Marshal` (struct to file) | 11.6 µs | | 15.5 KiB | 19 |
123+| `Set` (edit one key in place) | 2.4 µs | | 10.5 KiB | 5 |
124+| `Watch` (one write to one report, inotify) | 5.5 µs | | 256 B | 2 |
125+
126+Reproduce with:
127+
128+```sh
129+go test -run '^$' -bench . -benchmem -count 6 .
130+```
131+
110 ## License132 ## License
111 133
112 MIT134 MIT

Keyboard shortcuts

Single-key shortcuts are on. ctrl k and esc work whatever this says.

ctrl k :
go to a section, branch, tag, file or repository
?
this list
j k
move the row cursor down / up
enter
open the row under the cursor; on Files, a directory opens or closes in place
↑ ↓ ← → home end
in the file tree (focus on a row): previous / next row, close / open a directory or go to its parent / first entry, first / last row. They never open a file
l h
on Files: open a directory or a file / close a directory or go up to its parent, then to the parent page. Elsewhere: into the side panel (on a merge request, its files) / back to the content; there j k move between its controls
g g G
first / last row
/
filter the list; on Files, find a file anywhere in the repository (esc clears, enter opens the best match)
b
switch branch or tag
g s g f g c g b g m g i g r g a
tabs: summary, files, commits, branches & tags, merge requests, issues, releases, actions (when available)
g h
home
w
wide mode: use the whole width of the screen, or not (remembered)
y
copy a permalink pinned to the commit
d u x
diff: split / unified / collapse or expand all
e E
diff: the whole file in view / every file, with the lines the hunks hide
n
merge request: next note in the diff
esc
close a dialog, leave a field

Branches 1

Tags 3

↑↓ moveenter openesc close