Go🚀Advancedadvanced
unsafe Package
Go · Advanced · Run with go run
Explanation
The `unsafe` package bypasses Go's type system and memory safety guarantees. `unsafe.Pointer` converts between any pointer types. `unsafe.Sizeof` returns a type's size in bytes. It is used in performance-critical code (zero-copy string↔bytes conversion), CGo interop, and implementing low-level data structures. Incorrect use causes memory corruption — use only when absolutely necessary.
Real-World Scenario
High-performance JSON parsers (like `jsoniter`) use `unsafe.Pointer` to convert `[]byte` to `string` without copying — a safe operation when the string is not mutated, avoiding allocation in the hot path.
Quick Snippet
snippet.go
import "unsafe"
// Zero-copy []byte to string conversion (read-only use only)
func bytesToString(b []byte) string {
return *(*string)(unsafe.Pointer(&b))
}
// Inspect struct layout
type Point struct{ X, Y float32 }
p := Point{1.0, 2.0}
fmt.Println(unsafe.Sizeof(p)) // 8 bytes
fmt.Println(unsafe.Alignof(p)) // 4 bytes
// Access struct fields by offset
xPtr := (*float32)(unsafe.Pointer(&p))
yPtr := (*float32)(unsafe.Pointer(uintptr(unsafe.Pointer(&p)) + 4))
fmt.Println(*xPtr, *yPtr) // 1 2Full Example
unsafe_basics.go
// Compile: go run unsafe_basics.go
// Output:
// Point size: 8 bytes
// Point align: 4 bytes
// zero-copy string: hello
package main
import (
"fmt"
"unsafe"
)
type Point struct {
X, Y float32
}
// bytesToString converts without copying (read-only use only).
func bytesToString(b []byte) string {
if len(b) == 0 {
return ""
}
return unsafe.String(&b[0], len(b))
}
func main() {
p := Point{1.0, 2.0}
fmt.Println("Point size:", unsafe.Sizeof(p), "bytes")
fmt.Println("Point align:", unsafe.Alignof(p), "bytes")
b := []byte("hello")
fmt.Println("zero-copy string:", bytesToString(b))
}
Run command
go run unsafe_basics.go