Setelah mencari beberapa referensi untuk mengetahuinya, -sayangnya saya tidak bisa menemukan berguna dan sederhana - keterangan tentang memahami perbedaan antara melempar
dan rethrows
. Hal ini agak membingungkan ketika mencoba untuk memahami bagaimana kita harus menggunakan mereka.
Saya akan menyebutkan bahwa saya agak akrab dengan -default- melempar
dengan bentuk yang paling sederhana untuk menyebarkan kesalahan, sebagai berikut:
enum CustomError: Error {
case potato
case tomato
}
func throwCustomError(_ string: String) throws {
if string.lowercased().trimmingCharacters(in: .whitespaces) == "potato" {
throw CustomError.potato
}
if string.lowercased().trimmingCharacters(in: .whitespaces) == "tomato" {
throw CustomError.tomato
}
}
do {
try throwCustomError("potato")
} catch let error as CustomError {
switch error {
case .potato:
print("potatos catched") // potatos catched
case .tomato:
print("tomato catched")
}
}
So far So good, tapi masalah muncul ketika:
func throwCustomError(function:(String) throws -> ()) throws {
try function("throws string")
}
func rethrowCustomError(function:(String) throws -> ()) rethrows {
try function("rethrows string")
}
rethrowCustomError { string in
print(string) // rethrows string
}
try throwCustomError { string in
print(string) // throws string
}
apa yang saya tahu sejauh ini adalah ketika memanggil sebuah fungsi yang melempar
itu harus ditangani oleh coba-coba
, seperti rethrows
. Jadi apa?! Apa logika yang harus kita ikuti ketika memutuskan untuk menggunakan melempar
atau rethrows
?
Dari "Declarations" di Swift pesan:
Rethrowing Fungsi dan Metode
fungsi atau metode dapat dinyatakan dengan
rethrows
kata kunci untuk menunjukkan bahwa itu melempar kesalahan hanya jika salah satu dari fungsi itu parameter melempar kesalahan. Fungsi-fungsi ini dan metode yang dikenal sebagai rethrowing fungsi dan rethrowing metode. Rethrowing fungsi dan metode harus memiliki setidaknya satu melemparkan parameter fungsi.
Sebuah contoh khas adalah peta
metode:
public func map<T>(_ transform: (Element) throws -> T) rethrows -> [T]
Jika peta
yang disebut dengan non-lempar mengubah, tidak membuang
kesalahan itu sendiri dan dapat disebut tanpa mencoba
:
// Example 1:
let a = [1, 2, 3]
func f1(n: Int) -> Int {
return n * n
}
let a1 = a.map(f1)
Tapi jika peta
yang disebut dengan melemparkan penutupan lalu itu sendiri dapat membuang
dan harus dipanggil dengan mencoba
:
// 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 {
// ...
}
peta
dinyatakan sebagai melempar
bukan rethrows
maka anda akan
harus menyebutnya dengan mencoba
bahkan dalam contoh 1,
yang "nyaman" dan bloats kode yang tidak perlu. peta
yang dinyatakan tanpa melempar/rethrows
maka anda tidak bisa
panggilan itu dengan melemparkan penutupan seperti dalam contoh 2.Hal yang sama berlaku untuk metode lain dari Swift Standar Perpustakaan
yang mengambil parameter fungsi: filter()
, index(di mana:)
, forEach()
dan banyak banyak lagi.
Dalam kasus anda,
func throwCustomError(function:(String) throws -> ()) throws
menunjukkan fungsi yang dapat melempar kesalahan, bahkan jika disebut dengan non-melempar argumen, sedangkan
func rethrowCustomError(function:(String) throws -> ()) rethrows
menunjukkan fungsi yang melempar kesalahan hanya jika disebut dengan melemparkan argumen.
Secara kasar, rethrows
adalah untuk fungsi-fungsi yang tidak membuang
kesalahan "pada mereka sendiri", tetapi hanya "ke depan," kesalahan dari fungsi mereka
parameter.
Hanya untuk menambahkan sesuatu bersama dengan Martin's jawaban. Non melemparkan fungsi dengan tanda tangan yang sama seperti melemparkan fungsi dianggap sebagai sub-type
lempar fungsi. Itulah sebabnya rethrows dapat menentukan yang satu ini dan hanya memerlukan mencoba
ketika func param juga melempar, tetapi masih menerima fungsi yang sama tanda tangan yang doesn't melempar. It's cara yang nyaman untuk hanya harus menggunakan cobalah blok ketika func param melempar, tapi kode lain dalam fungsi doesn't melempar kesalahan.