class Bird {
var isFemale = true
func layEgg() {
if isFemale {
print("새가 알을 낳는다.")
}
}
func fly() {
print("새가 하늘로 날아간다.")
}
}
Eagle은 자동으로 isFemale과 layEgg() Fly()를 상속받음
class Eagle: Bird {
func soar() {
print("공중으로 치솟아 난다.")
}
}
Penguin은 날수없는데 Bird를 상속받아 어쩔수없이 fly()를 상속받게됨
class Penguin: Bird {
// fly()
func swim() {
print("헤엄친다.")
}
}
// 요구사항을 정의 (자격증의 필수 능력만 정의)
protocol SomeProtocol {
func playPiano()
}
→ SomeProtocol을 채택한 구조체,클래스는 무조건 playPiano()라는 함수를 구현
struct MyStruct: SomeProtocol {
func playPiano() {
print("피아노를 칩니다")
}
}
class MyClass: SomeProtocol {
func playPiano() {
print("나는 피아노를 칩니다")
}
}
struct FlyingMuseum1 {
func flyingDemo(flyingObject: CanFly) {
flyingObject.fly()
}
}
→ flyingDemo라는 함수에 파라미터로 “CanFly”라는 프로토콜을 채택하는 클래스나 구조체를 넣을 수 있다
protocol RemoteMouse {
// id를 읽을수만 있으면됨(let저장속성도 가능함 -> 쓰기 불가능함)
// -> 읽기 저장속성, 읽기만 가능한 계산속성, 읽기 쓰기 모두 가능한 계산속성
var id: String { get }
// name을 읽기도하고 쓰기도 해야함
// var 저장속성(let은 쓰기는불가능함❌), var 계산속성
var name: String { get set }
// 타입 저장 속성 (static), 타입 계산 속성 (class)
// 타입계산속성으로 하고 재정의를 하게하고 싶으면 아래 클래스에서 class로 구현해도됨
static var type: String { get set }
}
protocol RandomNumber {
// 최소한 타입 메서드가 되야함
// class로 구현해서 재정의를 허용하는 것도 가능
static func reset()
func random() -> Int
mutating func doSomething()
}
class Number: RandomNumber {
// 재정의 허락
class func reset() {
print("다시 셋팅")
}
// 재정의를 허락하지 않음
// static func reset() {
// print("다시 셋팅")
// }
func random() -> Int {
return Int.random(in: 1...100)
}
// 클래스이기때문에 mutating키워드가 필요가 없음
func doSomething() {
print("gg ")
}
}
protocol Togglable {
mutating func toggle()
}
enum OnOffSwitch: Togglable {
case on
case off
// 열거형(valueType)이기때문에 mutating키워드 붙여줘야함
mutating func toggle() {
switch self {
case .off:
self = .on
case .on:
self = .off
}
}
}
클래스라면????
class BigSwitch: Togglable {
var isOn = false
// mutating 키워드 필요없음 (클래스 이기 때문)
func toggle() {
isOn = isOn ? false : true
}
예제1
class SomeClass: SomeProtocol {
required init(num: Int) {
// 실제 구현
}
}
class SomeSubClass: SomeClass {
// 하위 클래스에서 생성자 구현 안하면 필수 생성자는 자동 상속
// required init(num: Int)
}
예제2
protocol AProtocol {
init()
}
class ASuperClass {
init() {
// 생성자의 내용 구현
}
}
class ASubClass: ASuperClass, AProtocol {
// AProtocol을 채택함으로 "required" 키워드 필요
// 상속으로 인한 "override(재정의)" 재정의 키워드도 필요
required override init() {
// 생성자의 내용 구현
}
}
protocol Certificate {
func doSomething()
}
class Person { }
// 관습적으로 본체보다는 확장에서, 채택하고 구현 (코드를 깔끔하게 정리 가능)
extension Person: Certificate {
func doSomething() {
print("Do something")
}
}