Dessa tre nyckelord hanterar uppskjuten körning och exceptionella situationer. defer planerar städning, panic utlöser en körningskrash (för verkligt exceptionella fall), och recover kan fånga en panic för att förhindra att programmet kraschar.
Dessa tre nyckelord hanterar uppskjuten körning och exceptionella situationer. defer planerar städning, panic utlöser en körningskrash (för verkligt exceptionella fall), och recover kan fånga en panic för att förhindra att programmet kraschar.
func readFile() error {
f, err := os.Open("file.txt")
if err != nil { return err }
defer f.Close() // GUARANTEED to run when readFile returns (any path)
// ... use f, with multiple return points ...
return nil // f.Close() runs here automatically
}
defer planerar ett funktionsanrop som ska köras när den omgivande funktionen returnerar — oavsett hur den returnerar (normal retur, fel eller panic). Det är det idiomatiska sättet att säkerställa städning: stänga filer, låsa upp mutexar, stänga anslutningar — placerat direkt bredvid förvärvet så att du inte kan glömma det.
defer fmt.Println("1")
defer fmt.Println("2")
defer fmt.Println("3")
// prints: 3, 2, 1 — last deferred, first executed (stack order)
func mustPositive(n int) {
if n < 0 {
panic("negative not allowed") // stops normal execution, unwinds the stack
}
}
// panic runs deferred functions as it unwinds, then crashes the program (with a stack trace)
panic stoppar normalt flöde och avvecklar anropsstacken (kör uppskjutna funktioner på vägen), vilket i slutändan kraschar programmet. Det är för programmeringsfel / oåterkalleliga villkor (utanför gränser, nil-dereference, omöjliga tillstånd) — INTE för vanliga fel (de använder returnerade error-värden).
func safeProcess() {
defer func() {
if r := recover(); r != nil { // recover() returns the panic value
fmt.Println("recovered from:", r) // handle it; program continues
}
}()
panic("something broke") // this panic is caught by the recover above
}
// safeProcess returns normally instead of crashing
recover återfår kontrollen över en panickande goroutine — men fungerar bara inuti en uppskjuten funktion. Det används sparsamt, t.ex. för att förhindra att en enskild request-handler kraschar en hel server.
Normal/expected failures (file missing, bad input, validation) → return an error value
panic/recover → reserve for TRULY exceptional cases (bugs, unrecoverable states)
and boundaries (e.g. a server recovering so one bad request doesn't kill the process)
defer är en väsentlig, idiomatisk Go-funktion för garanterad städning — placera resursfrigöring direkt bredvid förvärvet och säkerställ att den körs på varje returväg (inklusive panics), vilket förhindrar läckta filer, låsar och anslutningar mycket mer tillförlitligt än manuell städning.
Förstå även dess LIFO-ordning. panic/recover tillhandahåller en exceptionliknande mekanism, men den kritiska principen är att Go reserverar dem för verkligt exceptionella, oåterkalleliga situationer — normala fel bör alltid returneras som värden och kontrolleras.
Att missbruka panic/recover som generell exceptionhantering är oidiomatisk och ett vanligt misstag för utvecklare som kommer från exceptionbaserade språk.
Att veta när man använder defer (alltid, för städning), error-returer (normala misslyckanden) och panic/recover (sällsynt, exceptionellt eller vid gränser) är grundläggande för att skriva korrekt, idiomatisk Go och är ett vanligt intervjuämne.