It seems that go 1.22 has optimized the implementation of string to byte 
slicing and no longer requires memory allocation.


But why not optimize byte slicing to string conversion together?


```go
package main

import (
"reflect"
"testing"
"unsafe"
)


func BenchmarkString(b *testing.B) {
byteSli := []byte{123, 34, 100, 101, 102, 97, 117, 108, 116, 34, 58, 123, 
34, 99, 111, 109, 109, 111, 110, 34, 58, 123, 34, 112, 101, 116, 34, 58, 
123, 34, 102, 105, 118, 101, 34, 58, 34, 230, 150, 145, 230, 150, 145, 34, 
44, 34, 102, 111, 117, 114, 34, 58, 34, 231, 154, 174, 231, 147, 156, 231, 
147, 156, 34, 44, 34, 111, 110, 101, 34, 58, 34, 229, 188, 165, 229, 188, 
165, 230, 135, 181, 34, 44, 34, 116, 104, 114, 101, 101, 34, 58, 34, 229, 
145, 134, 229, 145, 134, 34, 44, 34, 116, 119, 111, 34, 58, 34, 233, 187, 
132, 230, 169, 153, 230, 169, 153, 34, 125, 44, 34, 114, 101, 108, 97, 116, 
105, 111, 110, 34, 58, 123, 34, 102, 97, 116, 104, 101, 114, 34, 58, 34, 
99, 117, 105, 120, 120, 120, 120, 120, 120, 120, 34, 44, 34, 109, 111, 116, 
104, 101, 114, 34, 58, 34, 121, 105, 110, 120, 120, 120, 120, 120, 34, 44, 
34, 119, 105, 102, 101, 34, 58, 34, 112, 101, 110, 103, 120, 120, 34, 125, 
125, 125, 125}

_ = string(byteSli)

}

func BenchmarkUnsafe(b *testing.B) {
byteSli := []byte{123, 34, 100, 101, 102, 97, 117, 108, 116, 34, 58, 123, 
34, 99, 111, 109, 109, 111, 110, 34, 58, 123, 34, 112, 101, 116, 34, 58, 
123, 34, 102, 105, 118, 101, 34, 58, 34, 230, 150, 145, 230, 150, 145, 34, 
44, 34, 102, 111, 117, 114, 34, 58, 34, 231, 154, 174, 231, 147, 156, 231, 
147, 156, 34, 44, 34, 111, 110, 101, 34, 58, 34, 229, 188, 165, 229, 188, 
165, 230, 135, 181, 34, 44, 34, 116, 104, 114, 101, 101, 34, 58, 34, 229, 
145, 134, 229, 145, 134, 34, 44, 34, 116, 119, 111, 34, 58, 34, 233, 187, 
132, 230, 169, 153, 230, 169, 153, 34, 125, 44, 34, 114, 101, 108, 97, 116, 
105, 111, 110, 34, 58, 123, 34, 102, 97, 116, 104, 101, 114, 34, 58, 34, 
99, 117, 105, 120, 120, 120, 120, 120, 120, 120, 34, 44, 34, 109, 111, 116, 
104, 101, 114, 34, 58, 34, 121, 105, 110, 120, 120, 120, 120, 120, 34, 44, 
34, 119, 105, 102, 101, 34, 58, 34, 112, 101, 110, 103, 120, 120, 34, 125, 
125, 125, 125}

_ = *(*string)(unsafe.Pointer(&byteSli))
}

func BenchmarkByteStyle(b *testing.B) {

str := 
`{"default":{"common":{"pet":{"five":"aa","four":"bb","one":"cc","three":"dd","two":"黄ee"},"relation":{"father":"ff","mother":"mm","wife":"ww"}}}}`

_ = []byte(str)

}

func BenchmarkWithUnsafe(b *testing.B) {

str 
:= 
`{"default":{"common":{"pet":{"five":"aa","four":"bb","one":"cc","three":"dd","two":"黄ee"},"relation":{"father":"ff","mother":"mm","wife":"ww"}}}}`

sh := (*reflect.StringHeader)(unsafe.Pointer(&str))
bh := reflect.SliceHeader{
Data: sh.Data,
Len:  sh.Len,
Cap:  sh.Len,
}
_ = *(*[]byte)(unsafe.Pointer(&bh))

}
```

```bench_test.go
package main

import (
"testing"
)


func BenchmarkTest1(b *testing.B) {
for i := 0; i < b.N; i++ {
BenchmarkString(b)
}
}

func BenchmarkTest2(b *testing.B) {
for i := 0; i < b.N; i++ {
BenchmarkUnsafe(b)
}
}

func BenchmarkTest3(b *testing.B) {
for i := 0; i < b.N; i++ {
BenchmarkByteStyle(b)
}
}

func BenchmarkTest4(b *testing.B) {
for i := 0; i < b.N; i++ {
BenchmarkWithUnsafe(b)
}
}
```

when go version is 1.21

```shell
 go version
go version go1.21.0 darwin/arm64

goos: darwin
goarch: arm64
pkg: bc
BenchmarkTest1-8        37078008                32.45 ns/op          192 
B/op          1 allocs/op
BenchmarkTest2-8        144106840                9.181 ns/op           0 
B/op          0 allocs/op
BenchmarkTest3-8        38973375                28.94 ns/op          192 
B/op          1 allocs/op
BenchmarkTest4-8        1000000000               0.3130 ns/op          0 
B/op          0 allocs/op
PASS
ok      bc      6.038s

```



when go version is 1.22

```shell
 go version                        
go version devel go1.22-631a6c2abf Fri Nov 17 23:34:11 2023 +0000 
darwin/arm64


 go test -test.bench=".*" -benchmem
goos: darwin
goarch: arm64
pkg: bc
BenchmarkTest1-8        35727334                33.51 ns/op          192 
B/op          1 allocs/op
BenchmarkTest2-8        147172425                8.157 ns/op           0 
B/op          0 allocs/op
BenchmarkTest3-8        1000000000               0.3136 ns/op          0 
B/op          0 allocs/op
BenchmarkTest4-8        1000000000               0.3153 ns/op          0 
B/op          0 allocs/op
PASS
ok      bc      5.095s
```



-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/ad5c54bb-157e-4b2b-8159-7d158cdb6d02n%40googlegroups.com.

Reply via email to