16.エラー処理(エラー処理、遅延)


エラー処理は、プログラムエラー条件下でエラーに応答し、応答するプロセスです.実行を完了するために常に有用な出力を生成できるタスクはありません.操作に失敗した場合、エラーの原因を理解してコードに応答させることは、通常、エラーハンドルを使用するために有用である.

エラーの表示とトレース(Throwing)

  • エラーは、Errorプロトコルのタイプに適合する値として表される.列挙型は、関連エラーの条件をモデリングするのに非常に適しており、関連値によってエラーの特性と情報をユーザーに伝えることができます.
  • enum VendingmachineError : Error {
    	case invalidSelection
        case insufficientFunds(coinsNeeded : Int)
        case outOfStock
    }
    
    //에러가 발생하면 예상치 못한 일이 발생하여 정상적 코드흐름이 불가능함을 나타낼 수 있다. 
    //throw구문을 사용해서 에러를 발생시킨다.
    throw VendingMachineError.insufficientFunds(coinsNeeded : 5)
    //다음과 같이 에러를 명시할 수 있다.

    エラー処理

  • エラーが発生した場合は、問題を修正したり、他の方法を試したり、ユーザーにエラーを通知する方法でエラーを処理したりする必要があります.スウィフ特有の4つのエラー処理方法.
  • 関数は、この関数を呼び出すコード
  • にエラーを伝播する.
  • do-catch構文
  • を使用
    エラー
  • の所望値で処理する
  • .
  • エラーなし、注
  • slowing関数を使用して、エラー伝播を指定できます.throwsで表される関数をthrow関数と呼ぶ.
  • func canThrowErrors() throws -> String {
     	//statement
    }
    //위의 메서드는 에러를 스로잉하는 함수이다. 
    //throwing함수는 에러를 전파만 가능하다. 던지기 선언이 되지 않은 함수에서 발생하는 모든 에러는
    //모두 함수 내에서 처리되어야 한다.
    
    struct Item {
    	var price : Int
        var count : Int
    }
    
    class VendingMachine {
    	var coinDeposit = 0
        
        func vend(itemNamed name : String) throws {
        	guard let item = inventory[name] else {
            	throws VendingMachineError.invalidSelection
            }
        }
    }
    //위에서 보는 것처럼 throw함수를 통해서 직접 에러를 스로잉 할 수 있다.
    
    func buyFavoriteSnack(person : String, vendingMachine : VendingMachine) throws {
    	let snackName = snackName ?? "Candy Bar"
        try vendingMachine.vend(itemNamed : snackNamed)
    }
    //다음과 같이 스로잉 함수를 호출할때는 앞에 try키워드를 붙여줘서 이 함수가 스로잉 함수임을 나타내준다.
  • Do-catchを使用してエラー処理を行います.do-catch構文でコードブロックを実行し、エラーを処理します.エラーがdoセクションで発生した場合、catchセクションと比較して、エラーを処理するアイテムを決定します.
  • do {
    	try expression
    } catch pattern 1 {
      // statement
    } catch pattern 2 {
    	//statement
    } catch pattern 3 {
    	//statement
    }
    //처리할 수 있는 에러가 무엇인지 나타내기 위해서 catch 뒤에 패턴을 작성한다. 
    
    var vendingMachine = VendingMachine()
    vendingMachine.coinDeposited = 8
    do {
    	try buyFavoriteSnack()
    } catch VendingMachineError.invalidSelection {
    	print("invalid Selection")
    } catch VendingMachineError.outOfStock {
    	print("Out of stock")
    } catch VendingMachineError.insufficient(let coinsNeeded) {
    	print("insufficient coins")
    } catch {
    	print("unexpected Error")
    }
    
    //다음과 같이 모든 에러 상황에 대한 클로저를 작성하여 수행작업을 지정할 수 있다.
    //try를 통해 호출하고 에러가 발생 시 catch 클로저로 진행된다.
    //catch절은 do 절에서 발생가능한 모든 에러를 처리할 필요는 없다.
  • エラーを外部値に変換できます.次の任務のためにtry?使用します.try?呼び出し間にエラーが発生した場合、式の値をnilに返します.
  • func someThrowingFunction() throws -> Int {
    	//statement
    }
    
    let x = try? someThrowingFunction()
    
    do {
    	y = try someThrowingFunction()
    } catch {
    	y = nil
    }
    
    //다음 함수에서 someThrowingFunction()이 에러를 발생시키면, x와 y의 값은 nil이다. 그렇지 않은 경우는 x와 y가 옵셔널 정수값을 가진다.
    //try?를 사용하면 모든 에러를 같은 방식으로 처리하려는 경우 간결하게 작성 가능하다.
    
    func fetchData() -> Data? {
    	if let data = try? fetchDataFromDisk() {
        	return data
        }
        if let data = try? fetchDataFromServer() {
        	return data
        }
        return nil // 에러를 다음과 같이 간단하게 처리한다.
    }
    
  • エラー伝播を無効にできます.トレース関数またはメソッドが実際に実行中にエラーがないことを知っている場合は、エラー伝播を無効にしてみてください.書くことも呼び出すこともできます.この場合、エラーが発生すると、ランタイムエラーが発生します.
  • let photo = try! loadImagE(atPath : "./Resource/John Appleseed.jpg")
    //옵셔널 강제 언래핑과 비슷하게 에러도 강제 언래핑 할 경우 런타임 오류가 난다.

    クリーンアップタスクの指定(defer)

  • コード実行の間で、現在のblockが終了する前の遅延構文を使用して、一連の構文を実行します.この構文では、エラーが発生して終了したり、return、breakなどの構文終了に必要なクリーンアップを実行したりすることができます.
  • 遅延文
  • は、現在の範囲が終了するまで実行を遅延する.
  • func processFile(filename : String) throws {
    	if exist(filename) {
        	let file = open(filename)
            defer {
            	close(file)
            }
            while let line = try file.readline() {
            	//work with the file
            }
            //close(file) is called here, at the end of scope
            //여기에서 defer에서 정의한 클로저가 실행된다.
        }
    }