Sobes.tech
Junior
139
questionbank

Какую роль в языке Go играет конструкция defer?

Ответ от нейросети

sobes.tech AI

Конструкция defer используется для планирования выполнения функции после завершения объемлющей функции, независимо от того, завершилась ли она успешно или с ошибкой. Это особенно полезно для освобождения ресурсов, таких как закрытие файлов или сетевых соединений, снятие блокировок.

Функции, объявленные с defer, выполняются в порядке, обратном их объявлению (LIFO - Last In, First Out).

Пример использования для закрытия файла:

package main

import (
	"fmt"
	"os"
)

func main() {
	f, err := os.Open("example.txt")
	if err != nil {
		fmt.Println("Ошибка открытия файла:", err)
		return
	}
	// Отложенное закрытие файла
	defer f.Close()

	// Дальнейшая работа с файлом
	fmt.Println("Файл успешно открыт")
	// При выходе из функции main() defer f.Close() будет вызван автоматически
}

Пример использования для освобождения блокировки:

package main

import (
	"fmt"
	"sync"
)

var mu sync.Mutex

func safeAccess() {
	mu.Lock()
	// Отложенное снятие блокировки
	defer mu.Unlock()

	// Критическая секция
	fmt.Println("Доступ к защищенному ресурсу")
}

func main() {
	safeAccess()
}

Важные моменты:

  • Аргументы функции, переданной в defer, вычисляются в момент объявления defer, а не при фактическом вызове отложенной функции.
  • Множественные defer в одной функции выполняются в порядке LIFO.
  • defer не может быть использован в глобальной области видимости.