Menu
CoddyTech

Вариативные функции (...)

Часть раздела Логика и управление потоком путешествия по Lua на Coddy. Урок 11 из 54.

Иногда нужна функция, которая может работать с любым количеством аргументов. Возможно, вы хотите вычислить сумму двух чисел, трёх или десяти, не создавая отдельные функции для каждого случая. В Lua для этого есть специальный синтаксис: три точки ...

Если поместить ... в список параметров функции, она станет функцией с переменным числом аргументов, принимающей любое количество аргументов:

function sum(...)
    -- Тело функции
end

Внутри функции ты снова можешь получить доступ к этим аргументам, используя .... Чтобы с ними было удобнее работать, можно упаковать их в таблицу с помощью фигурных скобок:

function sum(...)
    local args = {...}
    local total = 0
    for i = 1, #args do
        total = total + args[i]
    end
    return total
end

print(sum(5, 10, 15))  -- Вывод: 30
print(sum(1, 2, 3, 4, 5))  -- Вывод: 15

Выражение {...} создаёт таблицу в виде списка, содержащую все аргументы, переданные функции. Затем по этой таблице можно пройтись, как и по любой другой, используя оператор длины # или ipairs().

Это работает, пока ни один аргумент не равен nil. Значение nil оставляет в таблице пропуск, а оператор # ненадёжен для таблицы с пропусками. select("#", ...) всегда возвращает количество аргументов, включая аргументы со значением nil:

function countArgs(...)
    return select("#", ...)
end

print(countArgs(10, 20, 30))        -- Вывод: 3
print(countArgs(10, nil, 30, nil))  -- Вывод: 4
challenge icon

Задание

Легко

Напишите функцию calculateAverage, которая принимает любое количество числовых аргументов и возвращает их среднее значение.

Используйте вариативный синтаксис ..., чтобы принимать произвольное количество аргументов, упаковывать их в таблицу, вычислять их сумму и делить её на количество аргументов.

Примечание: Стартовый код (помеченный как "Don't touch this code") считывает числа из ввода, преобразует каждое из текста в число с помощью tonumber() и сохраняет их в таблице с именем numbers. В конце он вызывает вашу функцию, используя unpack(numbers), которая передаёт значения таблицы как отдельные аргументы, поэтому ваша функция получает их в виде .... Вам не нужно изменять этот код или подробно разбираться в нём; просто сосредоточьтесь на написании calculateAverage.

Логика:

  • Упакуйте все аргументы в таблицу с помощью {...}
  • Пройдите по таблице, чтобы вычислить сумму всех чисел
  • Разделите сумму на количество аргументов, чтобы получить среднее значение
  • Верните среднее значение в виде числа

Параметры:

  • ... (числа): Произвольное количество числовых аргументов

Возвращает: Среднее значение всех переданных чисел (число)

Попробуйте сами

-- Не трогайте этот код --
local numbers = {}
while true do
    local input = io.read()
    if input == nil or input == "" then
        break
    end
    local num = tonumber(input)
    if num then
        table.insert(numbers, num)
    end
end
-------------------------

function calculateAverage(...)
    -- Напишите код здесь
end
quiz iconПроверьте себя

В этом уроке есть небольшой тест. Начните урок, чтобы ответить на вопросы и сохранить прогресс.

Все уроки раздела Логика и управление потоком

Потренируйтесь самостоятельно: Онлайн-компилятор Lua