Почему этот average возвращает 1.0 для []int{1, 2} вместо 1.5?
Этот average должен возвращать среднее по срезу int как float64, но для []int{1, 2} возвращает 1.0 вместо 1.5.
func average(nums []int) float64 {
sum := 0
for _, n := range nums {
sum += n
}
return float64(sum / len(nums))
}
Найдите ошибку и объясните причину.
sum / len(nums) — это целочисленное деление, которое усекает к нулю до приведения float64(...) — 3 / 2 даёт 1, затем приводится к 1.0. Пустой срез к тому же паникует делением на ноль. Исправление — сперва привести: float64(sum) / float64(len(nums)) и проверять len(nums) == 0.
- ✗Приводить к
float64после деления, а не до него - ✗Забывать, что целочисленное деление усекает к нулю, а не округляет
- ✗Не проверять
len(nums) == 0, что паникует делением на ноль
- →Почему
float64(sum / len(nums))всё равно усекает, хотя результат — float? - →Какое значение даёт
5 / 2в Go и чем оно отличается от5.0 / 2?
Найдите ошибку
func average(nums []int) float64 {
sum := 0
for _, n := range nums {
sum += n
}
return float64(sum / len(nums)) // ОШИБКА
}
Почему 1.0, а не 1.5
Внутри float64(sum / len(nums)) сначала вычисляется sum / len(nums). Оба операнда — int, поэтому это целочисленное деление: 3 / 2 усекается к нулю и даёт 1. Только потом float64(1) приводит результат к 1.0. Приведение снаружи слишком поздно — дробная часть уже потеряна.
⚠️ Вдобавок при пустом срезе len(nums) == 0, и деление на ноль вызывает панику integer divide by zero.
✅ Исправление — приводить к float64 до деления и проверять пустоту:
func average(nums []int) float64 {
if len(nums) == 0 {
return 0
}
sum := 0
for _, n := range nums {
sum += n
}
return float64(sum) / float64(len(nums)) // 1.5
}