Swift - 구조체, 클래스

구조체, 클래스?

구조체와 클래스는 프로그래머가 데이터를 용도에 맞게 묶어 표현하고자 할 때 용이합니다. 구조체와 클래스는 프로퍼티와 메서드를 사용하여 데이터를 구조화하여 관리할 수 있습니다.

같은점

  • 값을 저장하기 위해 프로퍼티(저장 프로퍼티)를 정의할 수 있습니다. 연산 프로퍼티도 정의 가능합니다.
  • 기능 수행을 위해 메서드를 정의할 수 있습니다.
  • 서브스크립트 문법을 통해 구조체 또는 클래스가 가지는 값(프로퍼티)에 접근하도록 서브스크립트를 정의할 수 있습니다.
  • 초기화될 때의 상태를 지정하기 위해 이니셜라이저를 정의할 수 있습니다.
    • 구조체는 기본으로 멤버와이즈 이니셜라이저가 제공됩니다. 또, 사용자 정의 이니셜라이저도 구현이 가능합니다.
    • 클래스도 기본 이니셜라이저 외에 사용자가 직접 이니셜라이저를 정의할 수 있습니다.
  • 초기 구현과 더불어 새로운 기능 추가를 위해 익스텐션을 통해 확장할 수 있습니다.
  • 특정 기능을 수행하기 위해 특정 프로토콜을 준수(Adopt)할 수 있습니다.
  • 소스파일 하나에 여러 개의 구조체와 여러 개의 클래스를 정의하고 구현 가능합니다.
  • 중첩 함수와 마찬가지로 구조체 안에 구조체, 클래스 안에 클래스 등과 같이 중첩 타입의 정의 및 선언 가능합니다.

차이점

데이터를 구조화하여 관리하는 구조체와 클래스는 서로 같은 점도 있지만, 서로 차이점도 있습니다.

구조체 클래스
전통적인 OOP 관점에서의 클래스 C언어 등의 구조체보다 다양한 기능
참조 타입 값 타입
단일 상속 상속 불가
타입캐스팅 가능 타입캐스팅 불가
디이니셜라이저 가능 디이니셜라이져 불가
iOS 프레임워크의 대부분의 큰 뼈대는 모두 클래스로 구성 Swift의 대부분의 큰 뼈대는 모두 구조체로 구성

가장 큰 차이는 인스턴스의 타입입니다. 클래스의 인스턴스는 참조 타입이며 구조체의 인스턴스는 값 타입입니다. 값 타입과 참조 타입의 가장 큰 차이는 '무엇이 전달되느냐'입니다.

  • 어떤 함수의 전달인자로 값 타입의 값을 넘기면 전달될 값이 복사되어 전달됩니다.
  • 어떤 함수의 전달인자로 참조 타입의 값을 넘기면 참조(주소)가 전달됩니다.

인스턴스와 객체 흔히 다른 프로그래밍 언어에서는 클래스의 인스턴스를 객체라고 부릅니다. 물론 스위프트에서도 객체라고 표현하는 것이 틀린 것은 아니지만, 스위프트 공식 문서에는 좀 더 한정적인 인스턴스라는 용어를 사용합니다.

구조체와 클래스 선택해서 사용하기

구조체와 클래스는 모두 새로운 데이터 타입을 정의하고 기능을 추가한다는 점에서는 같습니다. 하지만 구조체 인스턴스는 항상 값 타입이고, 클래스 인스턴스는 참조 타입입니다. 그 의미는 생긴 것은 비슷하지만 용도는 다르다는 의미입니다. 프로젝트의 성격에 따라, 데이터의 활용 용도에 따라, 특정 타입을 구현할 때 구조체와 클래스 둘 중 하나를 선택해서 사용해야 합니다.

애플 가이드라인에 따른 구조체 사용 조건

  • 연관된 간단한 값의 집합을 캡슐화하는 것만이 목적일 때
  • 캡슐화된 값이 참조되는 것보다 복사되는 것이 합당할 때
  • 구조체에 저장된 프로퍼티가 값 타입이며 참조되는 것보다 복사되는 것이 합당할 때
  • 다른 타입으로부터 상속받거나 자신이 상속될 필요가 없을 때

글의 일부 내용은 야곰님의 저서 스위프트 프로그래밍(2017, 한빛미디어)를 참고하여 작성되었습니다.