본문 바로가기

iOS/Swift

Swift) Any와 AnyObject 알아보기

 

 

 

안녕하세요 :) 소들입니다! 

오늘은 타입 캐스팅의 연장선으로

 

Any

AnyObject

 

라는 "범용" 타입에 대해 공부해보려고 해요!!

모든 포스팅은 편의 말투로 합니다~!!

 

 

 

 

1. Any & Any Object

 

타입 캐스팅을 수행할 때 일반적으로 상속 관계에 있는 클래스끼리만 캐스팅이 가능하지만,

Any와 AnyObject 타입을 사용할 경우, 상속 관계에 있지 않아도 타입 캐스팅을 할 수 있다

 

타입 캐스팅 포스팅에서,

상속 관계에 있을 때 업캐스팅(as), 다운 캐스팅(as? as!)을 할 수 있다고 했음!!

근데, Any와 AnyObject 타입인 경우 상속관계가 아니어도 타입 캐스팅을 할 수 있다고 했잖음!?!

이제, 이것에 대해 알아볼 것임

그전에 Any와 AnyObject가 도대체 먼지부터 알아봅자 :)

 

 

 

1-1. Any : 모든 타입을 저장한다

 

여러분 Swift는 늘 말하지만, Type에 민감한 언어임

따라서 만약 배열을 Int형 배열로 선언 했으면,

 

 

var nums: [Int= []
 
nums.append(1)
nums.append(1.0)                 // Cannot convert value of type 'Double' to expected argument type 'Int'
nums.append("sodeul")            // Cannot convert value of type 'String' to expected argument type 'Int'
nums.append(false)               // Cannot convert value of type 'Bool' to expected argument type 'Int

 

 

Int형 외의 타입은 절대 저장하지 못하는 것이 Swift의 이치

다른 타입을 저장하려 하면, 너 Int형 아닌데? 하고 에러냄

 

근데!!!!

이 예민함을 뒤로하고 모든 타입을 저장할 수 있게 해주는 것이 바로 Any

따라서 만약 다음과 같이 자료형을 Any 타입으로 명시해주면,

 

 

var things: [Any= []
 
things.append(1)
things.append(1.0)
things.append("sodeul")
things.append(false)        
things.append(Human.init()))        
things.append({ print("I am Sodeul!") })        

 

 

Any 타입엔 Value 타입(구조체, 열거형), Reference 타입(클래스, 클로저)이건 상관 없이

모두 짬뽕해서 저장이 가능함!

 

아~ Any는 모든 타입을 포함할 수 있는 범용 타입이구나!

그럼 AnyObject는 뭘까 👀

 

 

 

1-2. AnyObject : 모든 클래스 타입을 저장한다

 

Any보다 타입 앞에 "클래스 타입"이라는 수식어가 하나 더 붙었음..!

맞음 Any는 구조체건 열거형이건 클래스건 어떤 타입이건 모두 허용했다면,

AnyObject는 한층 더 까다로워진 것임!!

 

타입이 AnyObject로 선언될 경우, "클래스 타입"만 저장할 수 있음

따라서, 다음과 같이 AnyObject 타입으로 배열을 선언할 경우,

 

 

var things: [AnyObject= []
 
things.append(1)                                // Argument type 'Int' expected to be an instance of a class
things.append(1.0)                              // Argument type 'Double' expected to be an instance of a class
things.append("sodeul")                         // Argument type 'String' expected to be an instance of a class
things.append(false)                            // Argument type 'Bool' expected to be an instance of a class
things.append(Teacher.init()))        
things.append({ print("I am Sodeul!") })        // Argument type '()->()' expected to be an instance of a class

 

 

클래스 타입인 Teacher 인스턴스를 제외하고는, 모두 에러가 뜸

구조체도 안되고, 열거형도 당근 안되고, Reference Type인 클로저라고 예외는 아님

(클래스 아니니까 ㅃㅃ)

 

다만, 저장하려는 객체의 타입이 클래스이기만 하면 돼서

 

 

things.append(Teacher.init()))        
things.append(Student.init()))        

 

 

이렇게 클래스 타입이 Human이고, Teacher이고 상관 없이

모든 클래스 객체를 저장할 수 있음!!!

 

이것이 바로 Any와 AnyObject의 차이점 🌚

 

 

 

 

2. Any & AnyObejct의 타입 캐스팅

 

2-1. as를 이용한 패턴 매칭(switch)

 

as가 업캐스팅 혹은 패턴 매칭에 쓰인다 했잖음!?!?

아까 Any 예제를 이어서 보면,

 

 

for thing in things {
    switch thing {
    case _ as Int:
        print("Int Type!")
    case _ as Double:
        print("Double Type!")
    case _ as String:
        print("String Type!")
    case _ as Human:
        print("Human Type")
    case _ as () -> ():
        print("Closure Type")
    default:
        print("something else")
    }
}

 

 

어려운 건 아니고, 이런 식으로 switch 문을 활용해서,

해당 타입일 경우(캐스팅에 성공한 경우) case문이 실행될 수 있게 할 수 있다...이런 말임!

 

 

 

2-2. as? as!를 이용한 다운캐스팅(Downcasting)

 

Any & AnyObject가 모든 타입을 저장할 수 있어 편해보이지만,

불편한 점도 많음!! 가장 대표적인 것인게,

 

 

var name: Any = "Sodeul"

 

 

이런 식으로 Any로 선언 했다고 해도, 이것은 ktx 타고 가면서 봐도 String 타입임

하지만 name에 대고 String의 메서드나 프로퍼티에 접근하려고 하면,

 

 

 

 

아무것도 자동완성이... 나오지 않음...

만약 억지로 String에서 제공해주는 함수를 쓰려고 해도

 

 

 

 

에러가 남... 왜냐...?

Any나 AnyObject는  런타임 시점에 타입이 결정되기 때문에,

컴파일 시점에 위와 같이 해당 타입에 대해 알 수 없음..! 때문에 해당 타입의 멤버에도 접근할 수 없음

 

따라서, 만약 Any 타입인 name을 String으로 사용하고 싶다면,

 

 

if var name = name asString {
    name.append("-_-")
}

 

 

이렇게 as나 as?를 통해, 다운캐스팅 한 후에 사용해주어야 함!!!

불편하쿤...

 

 

 

 

3. Any와 AnyObject를 남발하진 말자...!!

 

우리가 알고 있듯 Swift는 타입에 민감한 언어인데...  Any와 AnyObject는 그것에 반할 뿐더러..

런타임 시점에 타입이 결정나기 때문에, 만약 오류가 난다면 런타임 오류로 빠지게 됨

또한 Any로 선언될 경우, 타입 캐스팅 하기 전까진 매우 사용하기가 불편했음잖음..!?...

 

따라서, 잘 사용한다면 좋지만!!!

꼭 필요하지 않은 경우를 빼곤 남발하지 말잣.. :)

 

 

 

 

 

 

 

 

 

 

.

.

.

Any와 AnyObject 포스팅 간단하게 끝!!

혹시 잘못된 내용, 피드백, 궁금증은 언제든 댓글 주세요!!

 

 

 



Calendar
«   2024/05   »
1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31
최근 댓글
Visits
Today
Yesterday