Как можно измерить использование памяти в Go и что такое pprof?
Sobes Copilot
Получайте ответы в реальном времени
Ответ от нейросети
sobes.tech AI
Использование памяти в Go можно измерить несколькими способами:
-
runtime.MemStats: Предоставляет snapshot статистики использования памяти, включая размер кучи, количество объектов, сборки мусора и т.д. Полезен для получения общего представления о распределении памяти.
-
Профайлер pprof: Мощный инструмент для анализа производительности и использования ресурсов, включая память. Позволяет собирать профили использования кучи в разные моменты времени и анализировать их для выявления узких мест и утечек памяти.
-
debug.FreeOSMemory(): Принудительно возвращает память операционной системе. Может косвенно помочь понять, сколько памяти удерживает Go рантайм.
pprof (net/http/pprof) — это пакет в стандартной библиотеке Go, который интегрируется с профайлером pprof из пакета runtime/pprof. Он предоставляет HTTP-интерфейсы для сбора профилей различных ресурсов, включая CPU, кучу (память), блокировки, goroutine и мьютексы.
Чтобы использовать его:
- Импортировать
net/http/pprof. - Стартовать HTTP сервер.
- Перейти по соответствующим URL-адресам (
/debug/pprof/) для доступа к профилям. - Использовать утилиту
go tool pprofдля анализа собранных данных.
Пример использования runtime.MemStats:
import (
"fmt"
"runtime"
"time"
)
func main() {
var m runtime.MemStats
runtime.ReadMemStats(&m) // Читаем статистику памяти
fmt.Printf("Alloc = %v MiB", bToMb(m.Alloc))
fmt.Printf("\tTotalAlloc = %v MiB", bToMb(m.TotalAlloc))
fmt.Printf("\tSys = %v MiB", bToMb(m.Sys))
fmt.Printf("\tNumGC = %v\n", m.NumGC)
// Пример работы с памятью
_ = make([]byte, 1024*1024*10) // Выделяем 10MB
time.Sleep(100 * time.Millisecond) // Ждем, чтобы GC успел сработать
runtime.ReadMemStats(&m)
fmt.Printf("After allocation: Alloc = %v MiB", bToMb(m.Alloc))
fmt.Printf("\tTotalAlloc = %v MiB", bToMb(m.TotalAlloc))
fmt.Printf("\tSys = %v MiB", bToMb(m.Sys))
fmt.Printf("\tNumGC = %v\n", m.NumGC)
}
func bToMb(b uint64) uint64 {
return b / 1024 / 1024
}
Пример использования pprof в HTTP-сервере:
import (
_ "net/http/pprof" // Импортируем для регистрации хендлеров pprof
"net/http"
"log"
)
func main() {
log.Println(http.ListenAndServe(":6060", nil)) // Слушаем на порту 6060
}
После запуска этого кода можно перейти по адресу http://localhost:6060/debug/pprof/ и получить доступ к различным профилям. Для анализа кучи можно воспользоваться go tool pprof http://localhost:6060/debug/pprof/heap.