맛동산이

스위프트 스터디 8탄) 클래스와 구조체(Class and Structures) 본문

앱/Swift 문법

스위프트 스터디 8탄) 클래스와 구조체(Class and Structures)

진ddang 2023. 7. 9. 02:41

 

스위프트 공식문서를 참조하였습니다.



클래스(class) vs 객체(object) vs 인스턴스(instance)

먼저 클래스와 객체 그리고 인스턴스를 이해 해야한다.

유튜브 smile han 참조

클래스로 부터 만들어진 객체를 인스턴스라고 한다.

 


객체와 인스턴스의 차이

객체는 클래스로 부터 만들어진 구현할 대상이며, 인스턴스란 그렇게 구현된 객체중 메모리가 할당되어 실체화한 객체를 의미한다.

public class Animal {   ... } /* 객체와 인스턴스 */ public class Main {   public static void main(String[] args) {     Animal cat, dog; // '객체'      // 인스턴스화     cat = new Animal(); // cat은 Animal 클래스의 '인스턴스'(객체를 메모리에 할당)     dog = new Animal(); // dog은 Animal 클래스의 '인스턴스'(객체를 메모리에 할당)   } }   //참조 https://gmlwjd9405.github.io/2018/09/17/class-object-instance.html

이렇게 class를 통해서 cat, dog를 객체를 선언해주는 것이 객체이며, 거기에서 new라는 메모리할당 메소드를 사용하여 cat에 메모리를 할당해주게 되고 이렇게 할당된 cat이 인스턴스가 되는것이다.

따라서 객체를 인스턴스로 인스턴스를 객체로 이야기 해도 크게 문제될것은 없지만 엄밀히 따지자면, 선언되었을 경우와 그렇게 선언된것이 메모리에 할당된것이므로,

객체는 현실세계와 비슷한 추상적인 개념이라면, 인스턴스는 소프트웨어 세상에 할당된 객체에 가깝다.


그래서 다시한번 정리하자면,

클래스(class)

  • 객체를 만들어 내기 위한 설계도 혹은 청사진
  • 연관되어 있는 변수와 메서드의 집합

객체(object)

  • 소프트웨어 세계에 구현할 추상적인 대상
  • 클래스에 의해 선언된 추상적인 개념

인스턴스(instance)

  • 클래스를 기반으로 소프트웨어에 직접적으로 구현된 실체
  • 실체화된 객체로 메모리가 할당된다.

 

구조체(struct)

구조체의 선언과 구조체 인스턴스 생성

struct someStruct{  //구조체의 내용 	var width: Int = 0 	var height: Int = 0 } //구조체 인스턴스 생성 let structOne = someStruct()

 

구조체 프로퍼티 접근

구조체 프로퍼티 접근은 . 을 사용하여 접근할수 있다.

이를 통해서 맴버 초기화후 값을 복사하고 확인해보면

import UIKit  struct someStruct{     var width: Int     var height: Int }  let structOne = someStruct(width: 10, height: 20) print(structOne.width) // 10 print(structOne.height) // 20  var structTwo = structOne structTwo.width = 20 print(structOne.width) //10 print(structTwo.width) //20

이렇게 복사하고 나서도 원본값은 변화하지 않는다.

이를 통해서 구조체와 열거형은 값 타입이라는것을 알수 있으며, 따로 메모리에 올라가 있다는 사실을 알수 있다.

 

클래스의 기본 구조

class 클래스명 : 부모클래스 { 		// 프로퍼티 		// 인스턴스 메서드 		// 타입(type) 메서드(클래스 메서드) }

이렇게 선언을 하게 된다.

  • 프로퍼티 : 클래스 내에 포함되는 변수와 상수의 정의 집합
  • 인스턴스 메서드 : 객체가 호출하는 메서드 정의
  • 타입 메서드 : 클래스가 호출하는 메서드의 정의

 

프로퍼티(property)

프로퍼티를 선언할때는 3개의 조건이 있다.

  1. 초기값이 존재하거나
  1. init을 사용하여 초기화 하거나
  1. 옵셔널 변수로 선언(! 혹은 ?)

프로퍼티 선언 형태

class Man{ 	var age: Int =1 	var weight: Double = 3.5 //초기값 주기 	var height: Double?      //옵셔널 변수로 선언 }

 

프로퍼티의 종류(stored, calculated(computed) property)

프로퍼티의 종류는 2개가 된다.

stored propert, calculated(computed) property이다.

기본적으로 상수나 변수로 프로퍼티가 정의되는것은 stored property이다.

하지만 이러한 stored property를 계산하거나 검색하는 것을 통해 프로퍼티값을 주는 경우를 calculated property라고 하며 형태는 다음과 같다.

class Man{ 	var age: Int = 1 	var weight: Double = 3.5 	var manAge : Int{ 		get{  			return age+ 10 	} }

이렇게 calculated property를 사용할때는 getter과 setter을 사용할수 있다.

 

getter

getter은 setter가 존재하지 않는 경우에는 get을 생략할수 있다.

class Man{ 	var age: Int = 1 	var weight: Double = 3.5 	var manAge : Int{ 			return age+ 10 	} }

setter가 있는경우는 생략이 불가능 하다.

 

setter

setter는 프로퍼티의 값을 변경 해주는 방법이다.

이렇게 setter를 설정해 주면, 인스턴스를 생성하고 이러한 프로퍼티값에 접근할때 마다 getter와 setter함수를 통해 인스턴스의 프로퍼티값이 정해진다.

class Man{ 	var age: Int = 1 	var weight: Double = 3.5 	var manAge : Int{ 		get{  			return age+ 10 		} 	} 		set(usaAge){ 			age=usaAge + 11 	} }

따라서 이후에

var kim=Man() // age = 1 print(kim.manAge) //getter함수를 통해 1+10 // 11 print(kim.age) //  setter함수를 통해 age=1+11 // 12

이렇게 작동된다.

이때

newValue

를 사용하게 되면 usaAge처럼 전달해주는 프로퍼티를 생략할수 있게 되고 결과적으로는 다음과 같이 작성할수 있다.

class Man{ 	var age: Int = 1 	var weight: Double = 3.5 	var manAge : Int{ 		get{return age+ 10} 		set{ age= newValue + 11} 	} } var kim = Man() kim.manAge // 11 kim.manAge = 10 kim.age // 21

즉 setter를 사용하면, 외부에서 값을 지정해줘서 age값을 변경할수도 있다.

 

getter, setter 정리


조금 했갈렸는데 다시 보니

getter를 사용하면, 다른 프로퍼티 값을 가져와, 현재 프로퍼티에 값을 설정해주고

setter를 사용하면, setter가 있는 프로퍼티에 값을 설정해주면, 그 값을 통해 다른 프로퍼티에 값을 변경해준다.


 

self

현재 클래스 내 메서드나 프로퍼티를 가리킬 때 메서드나 프로퍼티 앞에 self.을 사용함, 자바스크립트의 this라고 생각해도 될것 같기도

보통 위에서 아래에서 인스턴스 init을 할때 변수명과 동일하다면, 헷갈리기 때문에 명확한 선언을 위해서 self를 사용한다.

import UIKit  class Man{     var age = 1     var weight:Double = 3.5     func display(){         print("\(age), \(weight)") 		}     init(yourAge: Int, yourWeight: Double){             self.age = yourAge             self.weight = yourWeight     } }      var kim : Man = Man(yourAge: 20, yourWeight: 67.5) kim.display() // 20, 67

인스턴스(instance)

인스턴스 선언 형태

인스턴스를 생성할때는 반듯이 다음과 같은 형태를 유지 해줘야한다.

class Man{ 	var 인스턴스명 : 클래스명 = 클래스명() 	var 인스턴스명 = 클래스명()    // 타입추론 }

 

인스턴스 초기화 함수 init()

import UIKit  class Man{     var age = 1     var weight:Double = 3.5     func display(){         print("\(age), \(weight)") 		}     init(yourAge: Int, yourWeight: Double){             age = yourAge             weight = yourWeight     } }      var kim : Man = Man(yourAge: 20, yourWeight: 67.5) kim.display() // 20, 67

이렇게 인스턴스생성시 초기값을 계속해서 바꾸면서 생성하고 싶으면 init을 사용하면 된다.

 

👉
인스턴스 메서드나, 클래스 메서드나 overloading을 지원한다.

 

클래스(class or type) 메서드(method)

클래스 메서드는 다음과 같은 형태를 가진다.

class Man{ //프로퍼티 선언 	var age=1 	var weight=3.5  //인스턴스 메소드 선언 	func display(){ 		print("\(age), \(weight)") 	}  //클래스 메소드 선언 	class func cM(){ 		print("cM은 클래스 메서드입니다.") 	} 	static func pM(){ 		print("pM은 클래스 메서드 입니다.") 	} } //인스턴스 선언 var kim = Man() var choi : Man = Man() //인스턴스 메소드 사용 kim.display() choi.display() //클래스 메소드 사용 Man.cM() Man.pM()	

즉 인스턴스 메소드는 인스턴스만 사용가능하고,

클래스 메소드는 클래스만 사용가능하다.

 

식별연산자

===나 !==는 두개의 변수가 동일한 클래스, 구조체의 인스턴스를 참조하고 있는지 아닌지 확인하는 연산자 이다.


내용이 너무 많아서 프로퍼티, 메소드, 서브스크립트와 같은 내용은 따로 정리하도록 하겠다.

 


Uploaded by

N2T
반응형