Ответ 1
От "Объявления" в книге Swift:
Повторные функции и методы
Функцию или метод можно объявить с помощью ключевого слова
rethrows
. указывают, что он выдает ошибку только в том случае, если одна из ее функций параметры выдают ошибку. Эти функции и методы известны как реверсивные функции и методы реорганизации. Повторные функции и методы должны иметь по крайней мере один параметр функции бросания.
Типичным примером является метод map
:
public func map<T>(_ transform: (Element) throws -> T) rethrows -> [T]
Если map
вызывается с не-бросающим преобразованием, он не бросает
сама ошибка и может быть вызвана без try
:
// Example 1:
let a = [1, 2, 3]
func f1(n: Int) -> Int {
return n * n
}
let a1 = a.map(f1)
Но если map
вызывается с закрытием бросания, то сам может бросить
и должен быть вызван с помощью try
:
// Example 2:
let a = [1, 2, 3]
enum CustomError: Error {
case illegalArgument
}
func f2(n: Int) throws -> Int {
guard n >= 0 else {
throw CustomError.illegalArgument
}
return n*n
}
do {
let a2 = try a.map(f2)
} catch {
// ...
}
- Если
map
были объявлены какthrows
вместоrethrows
, тогда вы нужно называть егоtry
даже в примере 1, который "неудобен" и раздувает код ненужным. - Если
map
были объявлены безthrows/rethrows
, тогда вы не смогли бы вызовите его с закрытием бросания, как в примере 2.
То же самое верно для других методов из стандартной библиотеки Swift
которые принимают параметры функции: filter()
, index(where:)
, forEach()
и многие другие.
В вашем случае
func throwCustomError(function:(String) throws -> ()) throws
обозначает функцию, которая может вызывать ошибку, даже если она вызвана аргумент без бросания, тогда как
func rethrowCustomError(function:(String) throws -> ()) rethrows
обозначает функцию, которая выдает ошибку, только если вызывается с метательный аргумент.
Грубо говоря, rethrows
- для функций, которые не бросают
ошибки "сами по себе", но только "передовые" ошибки от их функции
параметры.