Skip to content

Instantly share code, notes, and snippets.

@ajm188
Last active November 22, 2020 18:54
Show Gist options
  • Save ajm188/98042a2166f8e295c432e2198b038ce8 to your computer and use it in GitHub Desktop.
Save ajm188/98042a2166f8e295c432e2198b038ce8 to your computer and use it in GitHub Desktop.
Zero padding benchmarks
package strings
import (
"bytes"
"fmt"
"strings"
"testing"
)
var (
padResult string
zeroes = 2
)
func BenchmarkPadWithSprintf(b *testing.B) {
var (
padder string
result string
)
for i := 0; i < b.N; i++ {
padder = fmt.Sprintf("%%0%dd", zeroes)
result = fmt.Sprintf(padder, i)
}
padResult = result
}
func BenchmarkPadWithMinimalSprint(b *testing.B) {
var (
padder string
result string
)
for i := 0; i < b.N; i++ {
padder = "%0" + fmt.Sprint(zeroes) + "d"
result = fmt.Sprintf(padder, i)
}
padResult = result
}
func BenchmarkPadWithBuffer(b *testing.B) {
var result string
for i := 0; i < b.N; i++ {
s := fmt.Sprint(i)
buf := bytes.NewBuffer(nil)
for j := 0; j < zeroes-len(s); j++ {
buf.WriteString("0")
}
result = buf.String() + s
}
padResult = result
}
func BenchmarkPadWithBufferByte(b *testing.B) {
var result string
for i := 0; i < b.N; i++ {
s := fmt.Sprint(i)
buf := bytes.NewBuffer(nil)
for j := 0; j < zeroes-len(s); j++ {
buf.Write([]byte{'0'})
}
result = buf.String() + s
}
padResult = result
}
func BenchmarkPadWithStringBuffer(b *testing.B) {
var result string
for i := 0; i < b.N; i++ {
s := fmt.Sprint(i)
buf := &strings.Builder{}
for j := 0; j < zeroes-len(s); j++ {
buf.WriteString("0")
}
result = buf.String() + s
}
padResult = result
}
func BenchmarkPadWithStringBufferByte(b *testing.B) {
var result string
for i := 0; i < b.N; i++ {
s := fmt.Sprint(i)
buf := &strings.Builder{}
for j := 0; j < zeroes-len(s); j++ {
buf.Write([]byte{'0'})
}
result = buf.String() + s
}
padResult = result
}
func BenchmarkPadWithRepeat(b *testing.B) {
var result string
for i := 0; i < b.N; i++ {
result = strings.Repeat("0", zeroes)
}
padResult = result
}

With zeroes = 2:

Running tool: /usr/local/bin/go test -benchmem -run=^$ github.com/ajm188/playground/bench/strings -bench ^(BenchmarkPadWithSprintf|BenchmarkPadWithMinimalSprint|BenchmarkPadWithBuffer|BenchmarkPadWithBufferByte|BenchmarkPadWithStringBuffer|BenchmarkPadWithStringBufferByte|BenchmarkPadWithRepeat)$

goos: darwin
goarch: amd64
pkg: github.com/ajm188/playground/bench/strings
BenchmarkPadWithSprintf-8            	 6237045	       193 ns/op	      23 B/op	       2 allocs/op
BenchmarkPadWithMinimalSprint-8      	 6153098	       219 ns/op	      23 B/op	       2 allocs/op
BenchmarkPadWithBuffer-8             	14622043	        81.7 ns/op	      16 B/op	       1 allocs/op
BenchmarkPadWithBufferByte-8         	15127011	        82.5 ns/op	      16 B/op	       1 allocs/op
BenchmarkPadWithStringBuffer-8       	14942125	        80.1 ns/op	      16 B/op	       1 allocs/op
BenchmarkPadWithStringBufferByte-8   	14615377	       106 ns/op	      16 B/op	       1 allocs/op
BenchmarkPadWithRepeat-8             	45234685	        26.8 ns/op	       2 B/op	       1 allocs/op
PASS
ok  	github.com/ajm188/playground/bench/strings	10.964s

With zeroes = 200:

Running tool: /usr/local/bin/go test -benchmem -run=^$ github.com/ajm188/playground/bench/strings -bench ^(BenchmarkPadWithSprintf|BenchmarkPadWithMinimalSprint|BenchmarkPadWithBuffer|BenchmarkPadWithBufferByte|BenchmarkPadWithStringBuffer|BenchmarkPadWithStringBufferByte|BenchmarkPadWithRepeat)$

goos: darwin
goarch: amd64
pkg: github.com/ajm188/playground/bench/strings
BenchmarkPadWithSprintf-8            	 2155336	       562 ns/op	     432 B/op	       4 allocs/op
BenchmarkPadWithMinimalSprint-8      	 1985774	       646 ns/op	     440 B/op	       5 allocs/op
BenchmarkPadWithBuffer-8             	  897444	      1324 ns/op	     928 B/op	       7 allocs/op
BenchmarkPadWithBufferByte-8         	  901957	      1401 ns/op	     928 B/op	       7 allocs/op
BenchmarkPadWithStringBuffer-8       	 1828899	       655 ns/op	     728 B/op	       9 allocs/op
BenchmarkPadWithStringBufferByte-8   	 1769736	       670 ns/op	     728 B/op	       9 allocs/op
BenchmarkPadWithRepeat-8             	14318334	        83.3 ns/op	     208 B/op	       1 allocs/op
PASS
ok  	github.com/ajm188/playground/bench/strings	11.518s

With zeroes = 2000:

Running tool: /usr/local/bin/go test -benchmem -run=^$ github.com/ajm188/playground/bench/strings -bench ^(BenchmarkPadWithSprintf|BenchmarkPadWithMinimalSprint|BenchmarkPadWithBuffer|BenchmarkPadWithBufferByte|BenchmarkPadWithStringBuffer|BenchmarkPadWithStringBufferByte|BenchmarkPadWithRepeat)$

goos: darwin
goarch: amd64
pkg: github.com/ajm188/playground/bench/strings
BenchmarkPadWithSprintf-8            	  348314	      3307 ns/op	    4121 B/op	       5 allocs/op
BenchmarkPadWithMinimalSprint-8      	  367332	      3276 ns/op	    4129 B/op	       6 allocs/op
BenchmarkPadWithBuffer-8             	  108021	     10953 ns/op	    8642 B/op	      10 allocs/op
BenchmarkPadWithBufferByte-8         	  106500	     11408 ns/op	    8642 B/op	      10 allocs/op
BenchmarkPadWithStringBuffer-8       	  292899	      4133 ns/op	    9483 B/op	      14 allocs/op
BenchmarkPadWithStringBufferByte-8   	  263287	      4705 ns/op	    9483 B/op	      14 allocs/op
BenchmarkPadWithRepeat-8             	 3714966	       312 ns/op	    2048 B/op	       1 allocs/op
PASS
ok  	github.com/ajm188/playground/bench/strings	9.520s
@ajm188
Copy link
Author

ajm188 commented Nov 22, 2020

The Sprintf approaches start to overtake in terms of time around 25 zeroes, and in terms of memory allocations at 7 zeroes.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment