🔥 오버라이딩
서브클래스에서는 수퍼클래스로부터 상속받은 인스턴스 메서드, 타입 메서드, 인스턴스 속성, 타입 속성, 서브스크립트를 자신만의 구현으로 재정의할 수 있습니다. 이를 오버라이딩(Overriding)이라고 합니다.
오버라이딩을 하려면 재정의하려는 특성 앞에 override
키워드를 붙여주면 됩니다. 이는 의도적으로 오버라이딩을 하는 것임을 명확히 하고, 실수로 매칭되는 정의를 제공하지 않았음을 나타냅니다. 실수로 오버라이딩을 하면 예상치 못한 동작이 발생할 수 있고, override
키워드 없이 오버라이딩하면 컴파일 시 오류로 진단됩니다.
override
키워드는 또한 Swift 컴파일러가 오버라이딩하는 클래스의 수퍼클래스(또는 그 상위 클래스 중 하나)에 오버라이딩에 제공한 선언과 일치하는 선언이 있는지 확인하도록 합니다. 이 검사는 오버라이딩 정의가 올바른지 확인해줍니다.
수퍼클래스의 메서드, 속성, 서브스크립트 접근하기
서브클래스에서 메서드, 속성, 서브스크립트를 오버라이딩할 때, 때로는 오버라이딩의 일부로 기존 수퍼클래스 구현을 사용하는 것이 유용할 수 있습니다. 예를 들어, 기존 구현의 동작을 개선하거나, 상속된 변수에 수정된 값을 저장할 수 있죠.
이런 경우 super
접두사를 사용하여 수퍼클래스 버전의 메서드, 속성, 서브스크립트에 접근할 수 있습니다:
- 오버라이딩된 메서드
someMethod()
는 오버라이딩 메서드 구현 내에서super.someMethod()
를 호출하여 수퍼클래스 버전의someMethod()
를 호출할 수 있습니다. - 오버라이딩된 속성
someProperty
는 오버라이딩 getter나 setter 구현 내에서super.someProperty
로 수퍼클래스 버전의someProperty
에 접근할 수 있습니다. - 오버라이딩된 서브스크립트
someIndex
는 오버라이딩 서브스크립트 구현 내에서super[someIndex]
로 같은 서브스크립트의 수퍼클래스 버전에 접근할 수 있습니다.
메서드 오버라이딩하기
서브클래스 내에서 상속된 인스턴스 메서드나 타입 메서드를 오버라이딩하여 맞춤형 또는 대체 구현을 제공할 수 있습니다.
다음 예제는 Vehicle
의 새로운 서브클래스 Train
을 정의하고, Train
이 Vehicle
에서 상속받은 makeNoise()
메서드를 오버라이딩합니다:
class Train: Vehicle { override func makeNoise() { print("Choo Choo") } }
swift
Train
의 새 인스턴스를 생성하고 makeNoise()
메서드를 호출하면, Train
서브클래스 버전의 메서드가 호출되는 것을 볼 수 있습니다:
let train = Train() train.makeNoise() // "Choo Choo" 출력
swift
속성 오버라이딩하기
상속된 인스턴스 속성이나 타입 속성을 오버라이딩하여 자신만의 사용자 정의 getter와 setter를 제공하거나, 오버라이딩 속성이 기본 속성 값이 변경되는 것을 관찰할 수 있도록 속성 옵저버를 추가할 수 있습니다.
속성 Getters와 Setters 오버라이딩하기
상속된 속성이 원본에서 저장 속성으로 구현되었든 계산 속성으로 구현되었든 상관없이 어떤 상속된 속성이라도 오버라이딩하여 자신만의 사용자 정의 getter(및 적절한 경우 setter)를 제공할 수 있습니다. 서브클래스는 상속된 속성의 저장 또는 계산 특성을 모릅니다. 단지 상속된 속성에 특정 이름과 타입이 있다는 것만 알죠. 오버라이딩하는 속성의 이름과 타입을 항상 명시해야 컴파일러가 오버라이드가 같은 이름과 타입의 수퍼클래스 속성과 일치하는지 확인할 수 있습니다.
서브클래스 속성 오버라이드에서 getter와 setter를 모두 제공함으로써 상속된 읽기 전용 속성을 읽기-쓰기 속성으로 표현할 수 있습니다. 그러나 상속된 읽기-쓰기 속성을 읽기 전용 속성으로 표현할 수는 없습니다.
다음 예제는 Vehicle
의 서브클래스인 새로운 클래스 Car
를 정의합니다. Car
클래스는 기본 정수 값이 1
인 gear
라는 새로운 저장 속성을 도입하죠. Car
클래스는 또한 Vehicle
에서 상속받은 description
속성을 오버라이딩하여 현재 기어를 포함한 사용자 정의 설명을 제공합니다:
class Car: Vehicle { var gear = 1 override var description: String { return super.description + " in gear \(gear)" } }
swift
description
속성의 오버라이드는 super.description
을 호출하는 것으로 시작하는데, 이는 Vehicle
클래스의 description
속성을 반환합니다. 그런 다음 Car
클래스 버전의 description
은 현재 기어에 대한 정보를 제공하기 위해 이 설명 끝에 약간의 추가 텍스트를 덧붙입니다.
Car
클래스의 인스턴스를 생성하고 gear
와 currentSpeed
속성을 설정하면, description
속성이 Car
클래스 내에 정의된 맞춤형 설명을 반환하는 것을 볼 수 있습니다:
let car = Car() car.currentSpeed = 25.0 car.gear = 3 print("Car: \(car.description)") // Car: traveling at 25.0 miles per hour in gear 3
swift
속성 옵저버 오버라이딩하기
속성 오버라이딩을 사용하여 상속된 속성에 속성 옵저버를 추가할 수 있습니다. 이를 통해 해당 속성이 원래 어떻게 구현되었든 상관없이 상속된 속성의 값이 변경될 때 통지받을 수 있습니다. 속성 옵저버에 대한 자세한 내용은 속성 옵저버를 참조하세요.
다음 예제는 Car
의 서브클래스인 새로운 클래스 AutomaticCar
를 정의합니다. AutomaticCar
클래스는 현재 속도에 따라 자동으로 적절한 기어를 선택하는 자동 변속기가 있는 차를 나타냅니다:
class AutomaticCar: Car { override var currentSpeed: Double { didSet { gear = Int(currentSpeed / 10.0) + 1 } } }
swift
AutomaticCar
인스턴스의 currentSpeed
속성을 설정할 때마다, 속성의 didSet
옵저버는 새로운 속도에 적합한 기어를 선택하여 인스턴스의 gear
속성을 설정합니다. 구체적으로, 속성 옵저버는 새로운 currentSpeed
값을 10
으로 나누고, 가장 가까운 정수로 내림한 다음 1
을 더한 기어를 선택합니다. 속도가 35.0
이면 기어는 4
가 됩니다:
let automatic = AutomaticCar() automatic.currentSpeed = 35.0 print("AutomaticCar: \(automatic.description)") // AutomaticCar: traveling at 35.0 miles per hour in gear 4
swift
이렇게 오버라이딩을 통해 상속받은 특성을 재정의하고 필요에 맞게 변경할 수 있습니다. 오버라이딩은 상속의 유연성을 더해주는 강력한 기능이에요!