Skip to content

Commit f83102c

Browse files
apocelipesgopherbot
authored andcommitted
strconv: use generics to reduce redundant helper functions
Benchstat shows there are no noticeable performance changes here. Change-Id: If2250334fe6664986f044cbaabfa1bfc84f871f7 GitHub-Last-Rev: d41a498 GitHub-Pull-Request: #66266 Reviewed-on: https://go-review.googlesource.com/c/go/+/570935 Auto-Submit: Ian Lance Taylor <[email protected]> Reviewed-by: Ian Lance Taylor <[email protected]> LUCI-TryBot-Result: Go LUCI <[email protected]> Commit-Queue: Ian Lance Taylor <[email protected]> Reviewed-by: Robert Griesemer <[email protected]>
1 parent 2ab9218 commit f83102c

File tree

1 file changed

+15
-30
lines changed

1 file changed

+15
-30
lines changed

src/strconv/quote.go

Lines changed: 15 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -493,34 +493,20 @@ func unquote(in string, unescape bool) (out, rem string, err error) {
493493
}
494494
}
495495

496-
// bsearch16 returns the smallest i such that a[i] >= x.
497-
// If there is no such i, bsearch16 returns len(a).
498-
func bsearch16(a []uint16, x uint16) int {
499-
i, j := 0, len(a)
496+
// bsearch is semantically the same as [slices.BinarySearch] (without NaN checks)
497+
// We copied this function because we can not import "slices" here.
498+
func bsearch[S ~[]E, E ~uint16 | ~uint32](s S, v E) (int, bool) {
499+
n := len(s)
500+
i, j := 0, n
500501
for i < j {
501502
h := i + (j-i)>>1
502-
if a[h] < x {
503+
if s[h] < v {
503504
i = h + 1
504505
} else {
505506
j = h
506507
}
507508
}
508-
return i
509-
}
510-
511-
// bsearch32 returns the smallest i such that a[i] >= x.
512-
// If there is no such i, bsearch32 returns len(a).
513-
func bsearch32(a []uint32, x uint32) int {
514-
i, j := 0, len(a)
515-
for i < j {
516-
h := i + (j-i)>>1
517-
if a[h] < x {
518-
i = h + 1
519-
} else {
520-
j = h
521-
}
522-
}
523-
return i
509+
return i, i < n && s[i] == v
524510
}
525511

526512
// TODO: IsPrint is a local implementation of unicode.IsPrint, verified by the tests
@@ -554,25 +540,25 @@ func IsPrint(r rune) bool {
554540

555541
if 0 <= r && r < 1<<16 {
556542
rr, isPrint, isNotPrint := uint16(r), isPrint16, isNotPrint16
557-
i := bsearch16(isPrint, rr)
543+
i, _ := bsearch(isPrint, rr)
558544
if i >= len(isPrint) || rr < isPrint[i&^1] || isPrint[i|1] < rr {
559545
return false
560546
}
561-
j := bsearch16(isNotPrint, rr)
562-
return j >= len(isNotPrint) || isNotPrint[j] != rr
547+
_, found := bsearch(isNotPrint, rr)
548+
return !found
563549
}
564550

565551
rr, isPrint, isNotPrint := uint32(r), isPrint32, isNotPrint32
566-
i := bsearch32(isPrint, rr)
552+
i, _ := bsearch(isPrint, rr)
567553
if i >= len(isPrint) || rr < isPrint[i&^1] || isPrint[i|1] < rr {
568554
return false
569555
}
570556
if r >= 0x20000 {
571557
return true
572558
}
573559
r -= 0x10000
574-
j := bsearch16(isNotPrint, uint16(r))
575-
return j >= len(isNotPrint) || isNotPrint[j] != uint16(r)
560+
_, found := bsearch(isNotPrint, uint16(r))
561+
return !found
576562
}
577563

578564
// IsGraphic reports whether the rune is defined as a Graphic by Unicode. Such
@@ -593,7 +579,6 @@ func isInGraphicList(r rune) bool {
593579
if r > 0xFFFF {
594580
return false
595581
}
596-
rr := uint16(r)
597-
i := bsearch16(isGraphic, rr)
598-
return i < len(isGraphic) && rr == isGraphic[i]
582+
_, found := bsearch(isGraphic, uint16(r))
583+
return found
599584
}

0 commit comments

Comments
 (0)