Документация

Функциональные типы

У каждой функции есть специальный функциональный тип, состоящий из типов параметров и типа возвращаемого значения.

Пример:

func addTwoInts(a: Int, _ b: Int) -> Int {
  return a + b
}
func multiplyTwoInts(a: Int, _ b: Int) -> Int {
  return a * b
}

В данном примере объявлены две простые математические функции – addTwoInts и multiplyTwoInts. Каждая из этих функций принимает два значения типа Int и возвращает одно значение типа Int, содержащее результат математической операции.

Обе функции имеют тип (Int, Int) -> Int. Эта запись означает следующее:

«функция с двумя параметрами типа Int, возвращающая значение типа Int«.

Вот еще один пример, но уже функции без параметров и возвращаемого значения:

func printHelloWorld() {
  print("hello, world")
}

Эта функция имеет тип () -> Void, т. е. «функция без параметров, которая возвращает Void«.

Использование функциональных типов

В Swift с функциональными типами можно работать так же, как и с другими типами. Например, можно объявить константу или переменную функционального типа и присвоить ей функцию соответствующего типа:

var mathFunction: (Int, Int) -> Int = addTwoInts

Эта запись означает следующее:

«Объявить переменную mathFunction, имеющую тип «функция, принимающая два значения типа Int, и возвращающая одно значение типа Int«. Присвоить этой новой переменной указатель на функцию addTwoInts«.

Функция addTwoInts имеет тот же тип, что и переменная mathFunction, поэтому с точки зрения языка Swift такое присваивание корректно.

Теперь функцию можно вызывать с помощью переменной mathFunction:

print("Result: \(mathFunction(2, 3))")
// Выведет "Result: 5"

Той же переменной можно присвоить и другую функцию такого же типа – аналогично нефункциональным типам:

mathFunction = multiplyTwoInts
print("Result: \(mathFunction(2, 3))")
// Выведет "Result: 6"

Как и в случае с любым другим типом, вы можете не указывать тип явно, а предоставить Swift самостоятельно вывести функциональный тип при присваивании функции константе или переменной:

let anotherMathFunction = addTwoInts
// для переменной anotherMathFunction выведен тип (Int, Int) -> Int

Функциональные типы как типы параметров

Функциональные типы наподобие (Int, Int) -> Int могут быть типами параметров другой функции. Это позволяет определять некоторые аспекты реализации функции непосредственно во время ее вызова.

Следующий код печатает на экране результаты работы приведенных выше математических функций:

func printMathResult(_ mathFunction: (Int, Int) -> Int, _ a: Int, _ b: Int) {
    print("Result: \(mathFunction(a, b))")
}
printMathResult(addTwoInts, 3, 5)
// Выведет "Result: 8"

В этом примере объявлена функция printMathResult(_:_:_:), у которой есть три параметра. Первый параметр под названием mathFunction имеет тип (Int, Int) -> Int. Соответственно, аргументом этого параметра может быть любая функция такого же типа. Второй и третий параметры называются a и b и относятся к типу Int. Они служат для передачи двух входных значений для математической функции.

При вызове printMathResult(_:_:_:) получает в качестве входных данных функцию addTwoInts(_:_:) и два целочисленных значения 3 и 5. Затем она вызывает переданную функцию со значениями 3 и 5, а также выводит на экран результат 8.

Задача функции printMathResult(_:_:_:) заключается в том, чтобы печатать результат работы математической функции соответствующего типа. При этом конкретные детали этой математической функции не имеют значения – главное, чтобы она была подходящего типа. Все это позволяет безопасно управлять работой функции printMathResult(_:_:_:) непосредственно во время вызова.

Функциональные типы как возвращаемые типы

Функциональный тип можно сделать возвращаемым типом другой функции. Для этого нужно записать полный функциональный тип сразу же после возвратной стрелки (->) в возвращаемой функции.

В следующем примере объявлены две простые функции – stepForward(_:) и stepBackward(_:). Функция stepForward(_:) возвращает входное значение, увеличенное на единицу, а функция stepBackward(_:) – уменьшенное на единицу. Обе функции имеют тип (Int) -> Int:

func stepForward(_ input: Int) -> Int {
    return input + 1
}
func stepBackward(_ input: Int) -> Int {
    return input - 1
}

Следующая функция под названием chooseStepFunction(backward:) имеет возвращаемый (Int) -> Int. Функция chooseStepFunction(backward:) возвращает функцию stepForward(_:) или функцию stepBackward(_:) в зависимости от значения логического параметра backward:

func chooseStepFunction(backward: Bool) -> (Int) -> Int {
    return backward ? stepBackward : stepForward
}

Теперь с помощью chooseStepFunction(backward:) можно получать функцию, которая будет сдвигать значение влево или вправо:

var currentValue = 3
let moveNearerToZero = chooseStepFunction(backward: currentValue > 0)
// moveNearerToZero now refers to the stepBackward() function

В предыдущем примере мы определяли, нужно ли прибавить или отнять единицу, чтобы последовательно приблизить переменную currentValue к нулю. Изначально currentValue имеет значение 3, т. е. сравнение currentValue > 0 даст true, а функция chooseStepFunction(backward:), соответственно, возвратит функцию stepBackward(_:). Указатель на возвращаемую функцию хранится в константе moveNearerToZero.

Так как moveNearerToZero теперь ссылается на нужную функцию, можно использовать эту константу для отсчета до нуля:

print("Counting to zero:")
// Counting to zero:
while currentValue != 0 {
    print("\(currentValue)... ")
    currentValue = moveNearerToZero(currentValue)
}
print("zero!")
// 3...
// 2...
// 1...
// zero!

Если вы нашли ошибку, пожалуйста, выделите фрагмент текста и нажмите Ctrl+Enter.

Если вы нашли ошибку, пожалуйста, выделите фрагмент текста и нажмите Ctrl+Enter.

Если вы создавали аккаунт ранее...

Если Вы создавали аккаунт на старой версии сайта, а сейчас не можете зайти, то Вам нужно сделать следующее:

  1. Нажать "Забыли пароль?"
  2. Указать Ваш email в появившейся форме и нажать "Сбросить пароль"
  3. Вам на почту придет письмо с уникальной ссылкой, по которой вы сможете сбросить старый пароль и войти в свой аккаунт на новой версии сайта

Далее вы сможете заходить на сайт по email и паролю.

Сообщить об опечатке

Текст, который будет отправлен нашим редакторам: