Noções Básicas de Runtime
10 exemplos para você começar com Runtime & GC - 7 básicos e 3 intermediários.
Busque em todas as páginas da documentação
10 exemplos para você começar com Runtime & GC - 7 básicos e 3 intermediários.
mkdir rtdemo && cd rtdemo && go mod init example.com/rtdemo.main.go (ou arquivos separados no mesmo pacote) e execute com go run ..GODEBUG=gctrace=1 go run . (verboso; use em programas pequenos).runtime.ReadMemStats captura contadores do alocador e do GC.
package main
import (
"fmt"
"runtime"
)
func main() {
var ms runtime.MemStats
runtime.ReadMemStats(&ms)
fmt.Printf("alocação de heap: %d KiB\n", ms.HeapAlloc/1024)
fmt.Printf("goroutines: %d\n", runtime.NumGoroutine())
}HeapAlloc são os bytes atualmente alocados no heap (objetos alcançáveis).ReadMemStats para o mundo brevemente - não chame a cada requisição em caminhos críticos.go_memstats_* do Prometheus em produção em vez de consultar em manipuladores.Relacionado: O Runtime do Go: Scheduler, GC e Memória - modelo mental do runtime
Conte goroutines ativas para triagem de vazamentos.
package main
import (
"fmt"
"runtime"
"time"
)
func main() {
fmt.Println("início:", runtime.NumGoroutine())
go func() {
time.Sleep(200 * time.Millisecond)
}()
time.Sleep(10 * time.Millisecond)
fmt.Println("com worker:", runtime.NumGoroutine())
}WaitGroup ou envios bloqueados em canais.Relacionado: Pilhas de Goroutine e Crescimento de Pilha - custo de pilha por goroutine
Veja quantos Ps o scheduler usa.
package main
import (
"fmt"
"runtime"
)
func main() {
fmt.Println("NumCPU:", runtime.NumCPU())
fmt.Println("GOMAXPROCS:", runtime.GOMAXPROCS(0))
}GOMAXPROCS(0) lê a configuração atual sem alterá-la.Relacionado: Goroutines: Custo de Criação e Visão Geral do Agendamento - modelo GPM
Força uma coleta para medir o heap ativo após a limpeza.
package main
import (
"fmt"
"runtime"
)
func main() {
data := make([]byte, 10<<20) // 10 MiB
_ = data
runtime.GC()
var ms runtime.MemStats
runtime.ReadMemStats(&ms)
fmt.Printf("heap após GC: %d MiB\n", ms.HeapAlloc/(1<<20))
}runtime.GC() executa um ciclo completo e retorna quando concluído.HeapAlloc alto mesmo imediatamente após o GC.Relacionado: Coletor de Lixo: Tri-Color Mark-Sweep e Pacing - o que um ciclo faz
Inspecione o tempo cumulativo de pausa STW.
package main
import (
"fmt"
"runtime"
)
func main() {
var ms runtime.MemStats
runtime.ReadMemStats(&ms)
fmt.Printf("ciclos de GC: %d\n", ms.NumGC)
fmt.Printf("total de pausa: %d ms\n", ms.PauseTotalNs/1e6)
if ms.NumGC > 0 {
last := ms.PauseNs[(ms.NumGC+255)%256]
fmt.Printf("última pausa: %d µs\n", last/1e3)
}
}PauseNs é um buffer circular de durações de pausa recentes.GOGC ou GOMEMLIMIT sob carga.Relacionado: GOGC, GOMEMLIMIT e Finalizadores - botões de ajuste
Veja quantos objetos cada ciclo aloca.
package main
import (
"fmt"
"runtime"
)
func allocN(n int) {
for i := 0; i < n; i++ {
_ = make([]byte, 1024)
}
}
func main() {
var before runtime.MemStats
runtime.ReadMemStats(&before)
allocN(1000)
var after runtime.MemStats
runtime.ReadMemStats(&after)
fmt.Println("delta de mallocs:", after.Mallocs-before.Mallocs)
}Mallocs e Frees aumentam monotonicamente durante a vida útil do processo.go test -bench com benchmem relata alocações por operação.Relacionado: Análise de Escape e Alocação de Pilha vs. Heap - reduzindo alocações de heap
Retorna spans não utilizados para o SO após um pico.
package main
import (
"fmt"
"runtime"
"runtime/debug"
)
func main() {
_ = make([]byte, 50<<20)
runtime.GC()
debug.FreeOSMemory()
var ms runtime.MemStats
runtime.ReadMemStats(&ms)
fmt.Printf("heap ocioso: %d MiB\n", ms.HeapIdle/(1<<20))
}FreeOSMemory incentiva o retorno deles ao SO.Relacionado: Vazamentos de Memória em Go: Causas Comuns - padrões de vazamento
Imprime uma linha por ciclo de GC no stderr.
package main
func main() {
for i := 0; i < 1_000_000; i++ {
_ = make([]byte, 256)
}
}GODEBUG=gctrace=1 go run .GOGC.Relacionado: Melhores Práticas de Runtime e GC - fluxo de trabalho de ajuste de produção
Lê métricas estruturadas de GC e memória (Go 1.16+).
package main
import (
"fmt"
"runtime/metrics"
)
func main() {
samples := []metrics.Sample{
{Name: "/gc/heap/live:bytes"},
{Name: "/sched/goroutines:goroutines"},
}
metrics.Read(samples)
fmt.Println("heap ativo:", samples[0].Value.Uint64())
fmt.Println("goroutines:", samples[1].Value.Uint64())
}MemStats em exportadores.go doc runtime/metrics para o catálogo completo./gc/cycles/total:gc-cycles combina bem com perfis de CPU durante regressões de GC.Relacionado: Perfilamento de CPU e Heap com pprof - perfil sob carga
Correlaciona StackInuse com o fan-out de goroutines.
package main
import (
"fmt"
"runtime"
"sync"
)
func main() {
var wg sync.WaitGroup
for i := 0; i < 10_000; i++ {
wg.Add(1)
go func() {
defer wg.Done()
var buf [4096]byte // cresce a pilha se necessário
_ = buf
}()
}
wg.Wait()
var ms runtime.MemStats
runtime.ReadMemStats(&ms)
fmt.Printf("pilha em uso: %d MiB, goroutines: %d\n",
ms.StackInuse/(1<<20), runtime.NumGoroutine())
}StackInuse é a memória agregada da pilha em todas as goroutines.StackInuse rastrear a contagem de requisições linearmente.Relacionado: Pilhas de Goroutine e Crescimento de Pilha - regras de crescimento e cópia
Versões de Stack: Esta página foi escrita para Go 1.26.x (padrão Green Tea GC, go fix modernizers - verifique o patch na compilação), chi (última versão - verifique na compilação), gin (última versão - verifique na compilação), echo (última versão - verifique na compilação), google.golang.org/grpc (última versão - verifique na compilação), sigs.k8s.io/controller-runtime (última versão - verifique na compilação), kubebuilder (última versão - verifique na compilação), tinygo (última versão - verifique os alvos de placa na compilação), wazero (última versão - verifique na compilação) e golangci-lint (última versão - verifique o conjunto de linters na compilação).
Revisado por Chris St. John·Última atualização: 18 de jul. de 2026