일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
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 |
- 구름톤 유니브
- 세종대학교
- ios
- Kingfisher
- Optional
- WeatherKit
- 앱개발
- MVVM
- 스트럭트
- 동시성
- async
- 기초문법
- 이론
- 네트워크
- GCD
- 프로토콜
- 반응형
- mvc
- collectionview
- swift
- uikit
- 실습
- RxSwift
- SwiftUI
- 대표
- 토이프로젝트
- 학과별커뮤니티
- CS
- 옵셔널
- struct
- Today
- Total
스윞한 개발자
옵셔널 내부구조 파해치기!👊🏻 본문
안녕하세요! 오늘은 옵셔널 내부구조를 파해쳐보겠습니다!

옵셔널이 무엇인지에 대해서는 개발을 하신다면 다들 잘 알고 계실 거라 생각합니다! 오늘은 swift에서 제공되는 옵셔널의 내부구조를 한번 파해쳐보겠습니다.

주석까지 하면 전체 코드는 500줄이 넘기에 되기에 차근차근 살펴보겠습니다!
@frozen public enum Optional<Wrapped> : ~Copyable where Wrapped : ~Copyable {
case none
case some(Wrapped)
}
@frozen은 ABI 안전성을 보장하기 위해서라는데,,,ABI에 대해서는 나중에 더 상세히 다뤄보겠습니다!
옵셔널은 열거형으로 정의되며, 두 가지 케이스로 정의 됩니다.
1. none : 값이 없음을 나타냅니다. (nil)
2. some(Wrapped) : 값이 존재하며, Wrapped(제네릭) 타입입니다.
# 초기화
public init(_ some: consuming Wrapped)
let optionalValue = Optional(42)
옵셔널 타입은 값을 감싸는 형태로 초기화할 수 있습니다.
#래핑
public mutating func take() -> Wrapped?
var number: Int? = 42
if let unwrapped = number.take() {
print(unwrapped) // 42
}
print(number) // nil
위처럼 take 메서드는 옵셔널 타입의 값에서 래핑 된 값을 추출하고, 기존의 값을 nil로 설정합니다.
public static func ~= (lhs: _OptionalNilComparisonType, rhs: borrowing Wrapped?) -> Bool
또한 옵셔널은 ==,!= 연산자를 통해 nil과 비교할 수 있습니다.
public func map<E, U>(_ transform: (Wrapped) throws(E) -> U) throws(E) -> U? where E : Error, U : ~Copyable
public func flatMap<E, U>(_ transform: (Wrapped) throws(E) -> U?) throws(E) -> U? where E : Error, U : ~Copyable
@inlinable public var unsafelyUnwrapped: Wrapped { get }
* map 메서드는 Optional이 nil이 아닐 경우 wrapped 값을 transform을 통해 반환합니다.
(E: Error, U: 변환 결과 타입, ~Copyable: 참조 가능하지만 복사가 금지됨)
* flatMap 메서드는 Optional이 nil이 아닐 경우 wrapped 값을 클로저를 통해 변환합니다.
* unsafelyUnwrapped는 옵셔널 값을 강제로 언래핑하는 속성입니다.
public func encode(to encoder: any Encoder) throws
public init(from decoder: any Decoder) throws
public var debugDescription: String { get }
let a: Int? = 5
let b: Int? = nil
print(a.debugDescription) // "Optional(5)"
print(b.debugDescription) // "nil"
이 코드는 옵셔널 값을 인코딩, 디코딩할 때 사용하는 메서드입니다. 간단하게 인코딩/디코딩할 때 옵셔널로 선언된 값이 nil일 경우 인코더/디코더도 nil로 반환합니다.
debugDescription은 변수/상수로 선언된 값의 디버깅 문자열을 제공합니다.
마지막으로,
@inlinable public func hash(into hasher: inout Hasher)
public var hashValue: Int { get }
public func ?? <T>(
optional: consuming T?,
defaultValue: @autoclosure () throws -> T
) rethrows -> T where T: ~Copyable
*hash 메서드는 Optional 값을 해싱할 때 사용됩니다. Set, Dictionary 같은 컬렉션에 사용됩니다. 값이 nil인 경우, 고유한 nil 해시 값을 추가합니다.
*hashValue는 Optional 값의 해시 값을 정수로 반환합니다.
*?? 연산자. Optional 이 nil인 경우 기본값을 반환하는 메서드입니다. 하나는 필수 기본값, 다른 하나는 선택적 기본값을 받습니다.
이렇게 swift.Optional 코드 내부를 한번 살펴보았습니다. 내부구조를 모르고 단순히 옵셔널 래핑을 사용해 왔는데, 단순한 과정이지만 다른 내부 구조들을 살펴보는 것도 좋을 듯합니다!
더 유익한 포스팅으로 찾아오겠습니다. 감사합니다!

'Swift 이론' 카테고리의 다른 글
Image Cache에 대한 고찰 💭 (0) | 2025.01.09 |
---|---|
코드 사이닝? 프로비저닝 프로파일? 🤔 (1) | 2025.01.05 |
ViewController의 생명주기(+viewIsAppearing) 톺아보기 (3) | 2025.01.05 |
Kingfisher 캐싱 톺아보기 (0) | 2025.01.04 |
Saving Data - UserDefault에 대한 정리 (2) | 2025.01.01 |