lass Figure {
var name = "Unknown"
init(name: String) {
self.name = name
}
func draw() {
print("draw \(name)")
}
}
// Circle은 Figure에게 상속을 받는다.
class Circle: Figure {
var radius = 0.0
}
let c = Circle(name: "Circle")
c.radius //0
c.name // "Circle"
c.draw() // draw Circle
// final class는 상속이 불가하다.
final class Rectangle: Figure {
var width = 0.0
var height = 0.0
}
class Square: Rectangle {
// 에러!
}
class Figure {
var name = "Unknown"
init(name: String) {
self.name = name
}
func draw() {
print("draw \(name)")
}
}
// circle에도 draw가 있다 -> override
class Circle: Figure {
var radius = 0.0
override func draw() {
print("🌻")
}
}
let c = Circle(name: "Circle")
c.draw() //🌻
class Figure {
let name: String
init(name: String) {
self.name = name
}
func draw() {
print("draw \(name)")
}
}
class Rectangle: Figure {
var width = 0.0
var height = 0.0
override func draw() {
// Figure의 draw도 사용하고 싶다면!
super.draw()
print("⬛️ \(width) x \(height)")
}
}
class Square: Rectangle {
}
let s: Figure = Square(name: "Square")
//s.width // 에러
//s.height // 에러
s.name // "Square"
-> s는 Square이지만, Figure로 Upcasting을 하였기에 Figure의 Property에만 접근을 할 수 있다.
// s는 s: Figure = Square(name: "Square")로 upcasting이 되어있다.
let downcastedS = s as! Square
downcastedS.width // 0
downcastedS.height // 0
downcastedS.height // 0
단, 원본 클래스보다 아래인 클래스로 downcasting하는 것은 불 가능하다.
class Rhombus: Square {
var angle = 45.0
}
// 원본 클래스보다 아래인 클래스로 downcasting하는 것은 불 가능하다.
let dr = s as! Rhombus // 에러
아래와 같이 class들을 설정해주자.
class Figure {
let name: String
init(name: String) {
self.name = name
}
func draw() {
print("draw \(name)")
}
}
class Triangle: Figure {
override func draw() {
super.draw()
print("🔺")
}
}
class Rectangle: Figure {
var width = 0.0
var height = 0.0
override func draw() {
super.draw()
print("⬛️ \(width) x \(height)")
}
}
class Square: Rectangle {
}
class Circle: Figure {
var radius = 0.0
override func draw() {
super.draw()
print("🔴, \(radius)")
}
}
기본 꼴
expression is Type
let num = 123
num is Int // true
num is Double // false
num is String // false
let t = Triangle(name: "Triangle")
let r = Rectangle(name: "Rect")
let s = Square(name: "Square")
let c = Circle(name: "Circle")
r is Rectangle // true
r is Figure // true
r is Square // false
-> as?/ as!로 할 수 있다(Down Casting)
let t = Triangle(name: "Triangle")
let r = Rectangle(name: "Rect")
let s = Square(name: "Square")
let c = Circle(name: "Circle")
// 원래 형식으로 casting
t as? Triangle
t as! Triangle
// upcasting
var upcasted: Figure = s
// downcasting -> 아래 코드들은 에러가 나지 않는다.
upcasted as? Square
upcasted as! Square
upcasted as? Rectangle
upcasted as! Rectangle
upcasted as? Circle // nil
upcasted as! Circle // error
// Circle로 다운캐스팅이 되지않기에 아무일도 일어나지 않는다.
if let c = upcasted as? Circle {
print("text")
}
또 다른 예)
// [배열] 안에서는 가장 인접한 superclass로 다 upcasting된다. 즉 list는 Figure이다.
let list = [t, r, s, c]
// polymorphism -> 현재 figure로 upcastinge되어있다.
for item in list{
// 비록 figure로 되어있지만, 각자 override된 method가 실행이된다.
item.draw()
// radius를 가져오고싶다면? -> Circle로 downcasting을 하자.(optional로)
if let c = item as? Circle {
print(c.radius)
}
}
참고 및 출처자료 - https://zeddios.tistory.com/265
--> 다시 공부해보기
// Any를 사용하면 형식에 관계없이 모든 데이터를 저장할 수 있음
var data: Any = 1
data = 2.3
data = "str"
data = [1, 2, 3]
data = NSString()
var obj: AnyObject = NSString()
//obj = 1 // error
// Any, AnyObject를 사용할 경우, typecasting을 사용해주어야된다.
if let str = data as? String {
print(str.count)
} else if let list = data as? [Int]{
}
switch data{
case let str as String:
print(str.count)
case let list as [Int]:
print(list.count)
case is Double:
print("Double Value")
default:
break
}