반응형
** edwith - Swift 프로그래밍 입문 강의 참고 **
# 구조체 #
- swift 대부분 타입은 구조체로 되어 있습니다.
- 구조체는 값(value) 타입
- 타입이름은 대문자 카멜케이스를 사용하여 정의
// 구조체 기본 문법
struct /*이름*/ {
/* 구현부분 */
}
// 구조체 property 및 method 구현
struct Sample {
// 가변 프로퍼티 : 값 변경 가능
var mutableProperty: Int = 100
// 불변 프로퍼티 : 값 변경 불가능
let immutableProperty: Int = 100
// 타입 프로퍼티 : static 키워드 사용 - 타입 자체가 사용하는 프로퍼티
static var typeProperty:Int = 100
// 인스턴스 메서드 : 인스턴스가 사용하는 메서드
func instanceMethod() {
print("instance method")
}
// 타입 메서드 : static 키워드 사용 - 타입 자체가 사용하는 메서드
static func typeMethod() {
print("type method")
}
}
// 구조체 사용
var mutable: Sample = Sample() // 가변 인스턴스 생성
mutable.mutableProperty = 200
mutable.immutableProperty = 200 // 컴파일 오류 - 불변 프로퍼티이기 때문
let immutable: Sample = Sample() // 불변 인스턴스 생성
immutable.mutableProperty = 200 // 컴파일 오류 - 불변 인스턴스이기 때문, 만약 immutable이 구조체가 아닌 클래스였다면 200으로 변경 가능.
immutable.immutableProperty = 200 // 컴파일 오류
// 타입 프로퍼티 및 메서드
Sample.typeProperty = 300
Sample.typeMethod() // type method
// 인스턴스에서는 타입 프로퍼티나 타입 메서드를 사용할 수 없습니다.
mutable.typeProperty = 400 // 컴파일 오류
mutable.typeMethod() // 컴파일 오류
예시) 학생 구조체 만들어보기
struct Student {
var name: String = "unknown"
var 'class': String = "튤립" // 키워드도 '로 묶어주면 이름으로 사용 가능
// 타입 메서드
static func selfIntroduce() {
print("학생 타입 메서드입니다.")
}
// 인스턴스 메서드
func selfIntroduce() {
print("저는 \(self.class)반 \(name)입니다.")
}
}
Student.selfIntroduce() // 학생 타입 메서드입니다.
var myStudent: Student = Student()
myStudent.name = "빈빈"
myStudent.class = "장미"
myStudent.selfIntroduce() // 저는 장미반 빈빈입니다.
let yourStudent: Student = Student()
yourStudent.name = "지지" // 컴파일 오류 - Student가 구조체가 아닌 클래스였다면 가능.
yourStudent.selfIntroduce() // 저는 튤립반 unknown입니다.
# 열거형 #
- 타입이 명확할 경우, 열거형의 이름을 생략할 수 있습니다.
- switch 구문에서 사용하면 좋습니다.
// 열거형 사용
enum WeekDay {
case mon
case tue
case wed
case thu, fri, sat, sun
func printMessage() { // Swift의 열거형에는 메서드도 추가 가능
switch self {
case mon, tue, wed
print("월화수")
case thu, fri, sat, sun
print("목금토일")
}
}
}
var day: Weekday = Weekday.mon
day = .tue // 타입이 명확하기 때문에 이렇게 표현해도 가능.
print(day) // tue
WeekDay.tue.printMessage() // 월화수
rawValue (원시값)
- C언어의 enum처럼 정수값을 가질 수 있습니다.
- rawValue는 case별로 각각 다른 값을 가져야 합니다. (자동으로 1일 증가된 값이 할당)
- rawValue를 반드시 지닐 필요가 없다면 굳이 만들지 않아도 됨
enum Fruit: Int {
case apple = 0
case grape = 1
case peach
case mango = 0 // 오류 - apple과 원시값이 같아서. 같은 원시값이 있으면 안됨.
}
print(Fruit.peach.rawValue) // 2
// 정수 타입 뿐만 아니라, Hashable 프로토콜을 따르는 모든 타입을 원시값의 타입으로 지정할 수 있습니다.
enum School: String {
case elementary = "초등"
case middle = "중등"
case high = "고등"
case university
}
print(School.middle.rawValue) // 중등
print(School.university.rawValue) // university
// 열거형의 원시값 타입이 String일 때, 원시값이 지정되지 않았다면 case의 이름을 원시값으로 사용합니다.
원시값을 통한 초기화
- rawValue를 통해 초기화 할 수 있습니다.
- rawValue가 case에 해당하지 않을 수 있으므로, rawValue를 통해 초기화 한 인스턴스는 옵셔널 타입입니다.
// rawValue를 통해 초기화 한 열거형 값은 옵셔널 타입이므로 Fruit 타입이 아닌 Fruit? 타입.
let apple: Fruit? = Fruit(rawValue: 0)
// if-let 구문을 사용하면 rawValue에 해당하는 케이스를 곧바로 사용할 수 있습니다.
if let orange: Fruit = Fruit(rawValue: 5) {
print("rawValue 5에 해당하는 케이스는 \(orange)입니다.")
} else {
print("rawValue 5에 해당하는 케이스가 없습니다.")
}
// rawValue 5에 해당하는 케이스가 없습니다.
# Value Type(값 타입)과 Reference Type(참조 타입) 비교#
- Value Type(값 타입)
+ 열거형, 구조체
+ 상속 불가능
+ 데이터를 전달할 때 값을 복사하여 전달
- Reference Type(참조 타입)
+ 클래스
+ 상속 가능
+ 데이터를 전달할 때 값의 메모리 위치를 전달
struct ValueType {
var property = 1
}
class ReferenceType {
var property = 1
}
// 1. ValueType
let firstStructInstance = ValueType()
var secondStructInstance = firstStructInstance
secondStructInstance.property = 2
print(firstStructInstance) // 1
print(secondStructInstance) // 2
// 2. ReferenceType
let firstClassReference = ReferenceType()
let secondClassReference = firstClassReference
secondClassReference.property = 2
print(firstClassReference.property) // 2
print(secondClassReference.property) // 2
반응형
'iOS > Swift' 카테고리의 다른 글
Swift-5. 인스턴스 생성 및 소멸 (0) | 2023.02.24 |
---|---|
Swift-4. 클로저, 프로퍼티 (0) | 2023.02.24 |
Swift-2. 반복문, 옵셔널/옵셔널체이닝/옵셔널바인딩 (0) | 2023.02.24 |
Swift-1. 변수, 리스트, 함수 (0) | 2023.02.24 |
[Swift 5.5] Async / Await (0) | 2021.12.20 |
댓글