Swift는 복잡한 구조를 가진 값이 많이 등장한다. 그 중에서, 구조체, 열거형(enum), 튜플(Tuple) 같은 것에 대해 설명한다.


구조체(struct)

Swift는 클래스나 배열 등의 것 외에도 복잡한 성질을 가진 값이 있다. 이 대해 정리해 보겠다. 우선 "구조"부터 설명하겠다.

구조체는 값을 저장한 속성과 처리를 구현하는 메소드이다. 구조체를 이용하려면 먼저 정의를 작성하고 이를 바탕으로 인스턴스를 생성한다. ~라고하면 "어? 클래스와 같은 아니야?"라고 생각할지도 모르겠다.

분명히, 기본적인 구조와 구성는 클래스와 거의 동일하고, 속성과 메소드의 처리도 전혀 차이가 없자만, 섬세한 점에서 차이가 있다.

정의 struct를 사용

클래스의 정의는 "class 이름"형태로 작성되지만, 구조체의 경우 "struct 이름"이다. 속성과 메소드 작성은 클래스와 동일하다.

struct 이름 {
    ...... 속성, 메서드의 작성 ......
}

상속되지 않는다.

구조체는 클래스와 같은 객체 지향 구조를 가지고 있지 않는다. 어디까지나 "값과 처리를 하나로 묶기 위한 것"이며, 계승하여 새로운 구조체를 만들거나 할 수 없다.

이니셜라이저 필요 없다.

클래스는 인자가 없는 기본 이니셜라이저는 자동으로 제공되지만, 속성 값을 인수 가진 이니셜라이저 등은 추가 작성하지 않으면 안되지만, 이 구조체는 속성을 포함하면 그 값을 인수로 가지는 이니셜라이저가 자동으로 생성된다.

참조는 않는다.

이것은 중요하다. 클래스의 경우, 인스턴스를 작성하면 해당 참조가 변수에 할당되었다. 인스턴스는 메모리의 어딘가에 보관되어 그 위치를 나타내는 값(참조)을 변수에 넣고 조작한다. 따라서 인스턴스가 포함된 변수를 다른 변수에 할당한 경우에도 참조가 복사 될 뿐이므로, 두 변수도 동일한 인스턴스를 참조한다.

구조체는 이런 참조를 하지 않는다. 따라서 인스턴스를 할당한 변수를 반면에 변수에 할당하면 구조 자체가 복사되어 두 변수는 서로 다른 인스턴스를 갖게 된다. 이 차이는 확실히 알고 있어야 한다.

아래에 간단한 구조의 이용 예제를 보도록 하자.

struct MyData {
    var age:Int
    var name:String
     
    func getData() ->String {
        return "[\(name)(\(age))]"
    }
}
 
var data = MyData(age: 99, name: "Taro")
var data2 = data
data2.name = "Hanako"
data2.age = 24
println(data.getData())
println(data2.getData())

여기에서는 MyData 구조를 만들고 그 인스턴스를 만들어 사용하고 있다. 인스턴스 생성은 MyData(age : 99, name : "Taro")으로 하고 있지만, 이를 위한 이니셜라이저는 없다. Swift가 자동으로 이니셜라이저를 제공 해 주고 있는 것을 알 수 있다.

또한, 작성한 인스턴스 data를 그대로 data2에 대입하고 있지만, 속성 값을 변경하여 출력시켜 보면, 양자가 각각 별도의 인스턴스를 보유하고 있는 것을 알 수 있다.



열거형(enum)

enum은 한국어로 '열거형'라는 한다. 이는 여러 값 중 하나를 선택하는 경우에 사용된다.

이 enum은 "enum"라는 키워드를 사용하여 정의한다. 다음과 같은 형태이다.

enum 이름 {
    case1
    case2
    ...... 중략 ......
}

enum 후에 이름을 지정한다. 그리고 {} 내에 case를 사용하여 준비하는 값을 작성한다. 또는 case 후에 여러 값을 함께 쓸 수도 있다. 모두 동작은 동일하다.

enum 이름 {
    case1, 값2, ...
}

이렇게 생성된 enum은 '이름, 값'이라는 식으로 하여 값을 지정 사용할 수 있다.

enum은 "기본값"을 지정할 수 있다.

enum 이름 : 유형 {
    case1 = 기본값
    case2 = 기본값
    ......
}

클래스의 상속과 같은 느낌으로, enum의 이름 뒤에 기본값의 형식을 지정한다. 그리고 각각의 값 뒤에 등호(=)로 기본값을 할당한다. 이렇게 생성된 enum 값은 "rawValue"라는 속성을 호출하는 것으로 기본값을 얻을 수 있다.

그럼 실제 사용 예제를 보도록 하자.

enum Janken {
    case Choki
        case Goo
    case Paa
}

enum 가위바위보 : String {
    case Choki = "가위"
    case Goo = "바위"
    case Paa = "보"
}

var me = Janken.Goo
var you = 가위바위보.Goo
print(me)
print(you.rawValue)

위에 Janken과 가위바위보에 두 가지의 enum을 정의하고 사용하고 있다. 가위바위보에서는 각 값에 String의 기본값을 지정하고 있다.

Janken.Goo를 print하면 Goo라고 표시되지만, 가위바위보.Goo는 기본값인 "바위"가 표시된다.



튜플(Tuple)

튜플은 이미 여러번 등장 했었다. 종류가 다른 여러 값을 한곳에 모아 처리 할 수 있는 것이다. 이것은 다음과 같이 작성한다.

(값1, 값2, ...)

이와 같이, 단지 값을 () 안에 쉼표(,)로 구분하여 써 나가는 것만으로 튜플을 만들 수 있다. 이 안에 있는 값은 "〇〇.1"과 같이 튜플의 값을 저장한 변수 뒤에 점으로 번호를 지정하여 얻을 수 있다.

그러나 번호 지정 방식은 제대로 값 순서를 이해하고 있지 않으면 실수도 있다. 그래서 튜플에는 사전처럼 키 이름을 붙여 두는 것도 가능하게 되어 있다.

(키1 : 값1, 키2 : 값2, ...)

이렇게 작성된 튜플은 "〇〇.키"와 같이 숫자가 아닌 키를 사용하여 값을 꺼낼 수 있다. 이것은 단지 배열과 사전의 차이 같은 느낌 생각하면 좋을 것이다.

그럼 아래에 튜플도 사용 예제를 보도록 하자.

func MakeTuple(name:String, age:Int)->(name:String, age:Int) {
    return (name:name, age:age)
}

var me = MakeTuple("Yamada", age: 99)
var you = MakeTuple("Hanako", age: 36)

print(me.name)
print(you.age)

위 예제는 정해진 형식의 튜플을 만드는 기능을 제공하고, 이를 이용하여 튜플을 만들어 값을 표시하는 예제이다.

튜플은 원하는대로 값 구성을 만들 수 있기 때문에, 너무 자유로워서 반대로 내용이 뿔뿔이 흩어지고 질 수도 있는 문제도 있지만, 이런 식으로하면 같은 형식의 튜플을 만들 수 있다.


'Swift' 카테고리의 다른 글

[Swift] 프로토콜 및 확장  (0) 2017.12.10
[Swift] 함수 리터럴 및 클로저  (0) 2017.12.10
[Switf] 구조체, 열거형, 튜플  (0) 2017.12.09
[Swift] 배열과 사전  (0) 2017.12.09
[Swift] 클래스 기본  (0) 2017.12.09
[Swift] 함수  (0) 2017.12.09

+ Recent posts