mirror of
https://github.com/golang/go
synced 2024-11-05 11:56:12 -07:00
strings: simpler and slightly faster implementation of FieldsFunc
Removed the need for maintaining an extra variable in one of the inner loops, leading to a slight speed-up for short strings. Benchmarks run on a "quiet" MacBook Pro, 3.3GHz Dual-Core Intel Core i7, with 16GB 2133MHz LPDDR3 RAM running macOS 10.15.4. name old time/op new time/op delta FieldsFunc/ASCII/16-4 147ns ± 0% 144ns ± 1% -2.04% (p=0.000 n=4+5) FieldsFunc/ASCII/256-4 1.63µs ± 0% 1.59µs ± 1% -2.50% (p=0.008 n=5+5) FieldsFunc/ASCII/4096-4 30.0µs ± 0% 29.3µs ± 2% ~ (p=0.190 n=4+5) FieldsFunc/ASCII/65536-4 491µs ± 5% 473µs ± 2% ~ (p=0.095 n=5+5) FieldsFunc/ASCII/1048576-4 8.02ms ± 7% 7.85ms ± 4% ~ (p=0.548 n=5+5) FieldsFunc/Mixed/16-4 182ns ± 1% 181ns ± 4% ~ (p=0.357 n=5+5) FieldsFunc/Mixed/256-4 1.74µs ± 1% 1.74µs ± 1% ~ (p=0.881 n=5+5) FieldsFunc/Mixed/4096-4 34.9µs ± 2% 34.7µs ± 0% ~ (p=0.310 n=5+5) FieldsFunc/Mixed/65536-4 595µs ± 1% 589µs ± 2% ~ (p=0.095 n=5+5) FieldsFunc/Mixed/1048576-4 10.1ms ± 3% 9.8ms ± 2% ~ (p=0.095 n=5+5) name old speed new speed delta FieldsFunc/ASCII/16-4 109MB/s ± 1% 111MB/s ± 1% +2.33% (p=0.008 n=5+5) FieldsFunc/ASCII/256-4 157MB/s ± 0% 161MB/s ± 1% +2.57% (p=0.008 n=5+5) FieldsFunc/ASCII/4096-4 137MB/s ± 0% 140MB/s ± 2% ~ (p=0.190 n=4+5) FieldsFunc/ASCII/65536-4 134MB/s ± 4% 139MB/s ± 2% ~ (p=0.095 n=5+5) FieldsFunc/ASCII/1048576-4 131MB/s ± 6% 134MB/s ± 4% ~ (p=0.548 n=5+5) FieldsFunc/Mixed/16-4 87.8MB/s ± 1% 88.3MB/s ± 4% ~ (p=0.421 n=5+5) FieldsFunc/Mixed/256-4 147MB/s ± 1% 147MB/s ± 1% ~ (p=0.841 n=5+5) FieldsFunc/Mixed/4096-4 117MB/s ± 2% 118MB/s ± 0% ~ (p=0.310 n=5+5) FieldsFunc/Mixed/65536-4 110MB/s ± 1% 111MB/s ± 2% ~ (p=0.095 n=5+5) FieldsFunc/Mixed/1048576-4 104MB/s ± 3% 107MB/s ± 2% ~ (p=0.095 n=5+5) name old alloc/op new alloc/op delta FieldsFunc/ASCII/16-4 32.0B ± 0% 32.0B ± 0% ~ (all equal) FieldsFunc/ASCII/256-4 352B ± 0% 352B ± 0% ~ (all equal) FieldsFunc/ASCII/4096-4 21.9kB ± 0% 21.9kB ± 0% ~ (all equal) FieldsFunc/ASCII/65536-4 448kB ± 0% 448kB ± 0% ~ (all equal) FieldsFunc/ASCII/1048576-4 8.85MB ± 0% 8.85MB ± 0% ~ (p=0.738 n=5+5) FieldsFunc/Mixed/16-4 48.0B ± 0% 48.0B ± 0% ~ (all equal) FieldsFunc/Mixed/256-4 416B ± 0% 416B ± 0% ~ (all equal) FieldsFunc/Mixed/4096-4 21.5kB ± 0% 21.5kB ± 0% ~ (all equal) FieldsFunc/Mixed/65536-4 448kB ± 0% 448kB ± 0% ~ (all equal) FieldsFunc/Mixed/1048576-4 8.85MB ± 0% 8.85MB ± 0% ~ (p=0.690 n=5+5) name old allocs/op new allocs/op delta FieldsFunc/ASCII/16-4 1.00 ± 0% 1.00 ± 0% ~ (all equal) FieldsFunc/ASCII/256-4 1.00 ± 0% 1.00 ± 0% ~ (all equal) FieldsFunc/ASCII/4096-4 5.00 ± 0% 5.00 ± 0% ~ (all equal) FieldsFunc/ASCII/65536-4 12.0 ± 0% 12.0 ± 0% ~ (all equal) FieldsFunc/ASCII/1048576-4 24.0 ± 0% 24.0 ± 0% ~ (all equal) FieldsFunc/Mixed/16-4 1.00 ± 0% 1.00 ± 0% ~ (all equal) FieldsFunc/Mixed/256-4 1.00 ± 0% 1.00 ± 0% ~ (all equal) FieldsFunc/Mixed/4096-4 5.00 ± 0% 5.00 ± 0% ~ (all equal) FieldsFunc/Mixed/65536-4 12.0 ± 0% 12.0 ± 0% ~ (all equal) FieldsFunc/Mixed/1048576-4 24.0 ± 0% 24.0 ± 0% ~ (all equal) Change-Id: I06828d798ca1a624a26edd7f7b68c3bf2fc28f84 Reviewed-on: https://go-review.googlesource.com/c/go/+/229765 Reviewed-by: Martin Möhrmann <moehrmann@google.com>
This commit is contained in:
parent
71e0cd815d
commit
e193725184
@ -379,25 +379,29 @@ func FieldsFunc(s string, f func(rune) bool) []string {
|
||||
spans := make([]span, 0, 32)
|
||||
|
||||
// Find the field start and end indices.
|
||||
wasField := false
|
||||
fromIndex := 0
|
||||
for i, rune := range s {
|
||||
// Doing this in a separate pass (rather than slicing the string s
|
||||
// and collecting the result substrings right away) is significantly
|
||||
// more efficient, possibly due to cache effects.
|
||||
start := -1 // valid span start if >= 0
|
||||
for end, rune := range s {
|
||||
if f(rune) {
|
||||
if wasField {
|
||||
spans = append(spans, span{start: fromIndex, end: i})
|
||||
wasField = false
|
||||
if start >= 0 {
|
||||
spans = append(spans, span{start, end})
|
||||
// Set start to a negative value.
|
||||
// Note: using -1 here consistently and reproducibly
|
||||
// slows down this code by a several percent on amd64.
|
||||
start = ^start
|
||||
}
|
||||
} else {
|
||||
if !wasField {
|
||||
fromIndex = i
|
||||
wasField = true
|
||||
if start < 0 {
|
||||
start = end
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Last field might end at EOF.
|
||||
if wasField {
|
||||
spans = append(spans, span{fromIndex, len(s)})
|
||||
if start >= 0 {
|
||||
spans = append(spans, span{start, len(s)})
|
||||
}
|
||||
|
||||
// Create strings from recorded field indices.
|
||||
|
Loading…
Reference in New Issue
Block a user