상세 컨텐츠

본문 제목

iOS프로그래밍_4주차_클래스(class) 상속

2026년도 1학기/iOS프로그래밍

by 멈뭉밈 2026. 3. 30. 15:17

본문

 

 

 

 

첫 번째 외부매개변수명만 생략하는, 4번째 방법을 제일 많이 사용한다.

 


1.

func add(x: Int, y: Int) -> Int

함수명: add(x:y:)

 

2. 

func add(first x: Int, second y: Int) -> Int

함수명: add(first:second:)


3.

func add(_ x: Int, _ y: Int) -> Int

함수명: add(_:_) → 외부 매개변수명 없음


4. 

func add(_ x: Int, with y: Int) -> Int

함수명: add(_:with:)


핵심 정리

  • Swift는 외부 매개변수 이름까지 포함해서 함수를 구분한다.
    → 그래서 오버로딩 가능

 

함수 코드

func tableView(_ tableView: UITableView,
               numberOfRowsInSection section: Int) -> Int {
    return items.count
}

1. 함수명 (호출 시 기준)

Swift에서 함수명은 외부 매개변수 라벨까지 포함해서 본다.

그래서 이 함수의 이름은 :

tableView(_:numberOfRowsInSection:)

_는 첫 번째 외부 라벨이 없다는 의미
두 번째는 numberOfRowsInSection


2. 함수 타입 (자료형)

규칙: (매개변수 타입들) -> 반환 타입

(UITableView, Int) -> Int

정리

구분내용

함수명 tableView(_:numberOfRowsInSection:)
함수 타입 (UITableView, Int) -> Int

이해 포인트

  • 함수명 → 외부 라벨 포함
  • 함수 타입 → 타입만, 라벨은 제거

한 줄 요약

이름은 라벨까지, 타입은 타입만 본다

 

 

 


 

 

func print(
    _ items: Any...,
    separator: String = " ",
    terminator: String = "\n"
)

 

 

https://chatgpt.com/s/t_69c2225cb834819193abb9e5f7dbe726

 

함수명 오버로딩 설명

ChatGPT가 답변을 듣고, 영감을 얻고, 생산력을 높이는 데 도움을 드립니다.

chatgpt.com

 

 


 

 

func up(num: Int) -> Int {
    return num + 1
}
func down(num: Int) -> Int {
    return num - 1
}
let toUp = up // Swift 함수는 일급 객체로, 변수나 상수에 저장할 수 있음
print(up(num: 5))
toUp(10)
// print(up(num:10))
// print(toUp(10)) //주의 : argument label인 (num:) 안 씀
// 함수를 변수에 할당하면 argument label(num:)을 생략해야 함
let toDown = down
print(toDown(20))

 

함수를 어떤 변수에 저장할 수 있지만 그 변수로 함수를 호출할 때는 argument label 을 쓰지 않아도 된다.

 

 


 

 

 

 

colorChangeTimer = Timer.scheduledTimer(withTimeInterval: 1.0, repeats: true) { timer in
    let red = CGFloat(arc4random_uniform(256)) / 255.0
    let green = CGFloat(arc4random_uniform(256)) / 255.0
}

 

 

 

 


 

 

 

자료형

 

 


 

 

 

 

 

후행 클로저를 자동으로 만들려면 파란 부분에서 엔터키를 누르면 자동으로 클로저로 바뀐다.

 

 


 

 

 


 

 

 

 

 

시험범위(꼭나옴 $표시 위주로)

 

 

1️⃣ 클로저 기본 형태 (가장 풀버전)

 
let add = {(val1: Int, val2: Int) -> Int in
return val1 + val2
}
 

구조 분석:

부분의미
{} 클로저 시작
(val1: Int, val2: Int) 매개변수
-> Int 반환 타입
in 매개변수와 실행 코드 구분
return 반환값

즉:

두 Int 받아서 Int 반환하는 익명 함수


2️⃣ 클로저를 함수에 전달

함수가 이렇게 있다고 가정:

 
func math(x: Int, y: Int, cal: (Int, Int) -> Int) -> Int {
return cal(x, y)
}
 

사용:

 
result = math(x: 10, y: 20, cal: add)
 

즉:

add 클로저를 cal 자리에 넣은 것


3️⃣ 클로저를 직접 작성해서 전달

변수 없이 바로 넣기:

 
result = math(x: 10, y: 20, cal: {(val1: Int, val2: Int) -> Int in
return val1 + val2
})
 

즉:

클로저를 inline으로 작성


4️⃣ trailing closure 문법

클로저가 마지막 매개변수이면 괄호 밖으로 이동 가능

 
result = math(x: 10, y: 20) {(val1: Int, val2: Int) -> Int in
return val1 + val2
}
 

여기서

cal:
 

생략됨

이걸 trailing closure라고 합니다.


5️⃣ 타입 추론으로 반환형 생략

Swift는 타입을 이미 알고 있음

(Int, Int) -> Int
 

그래서 생략 가능

 
result = math(x: 10, y: 20) {(val1: Int, val2: Int) in
return val1 + val2
}
 

6️⃣ shorthand argument name 사용 ($0, $1)

매개변수 이름도 생략 가능

 
result = math(x: 10, y: 20) {
return $0 + $1
}
 

의미:

기호의미
$0 첫 번째 매개변수
$1 두 번째 매개변수

7️⃣ return 생략 가능

클로저가 한 줄이면 자동 반환됨

 
result = math(x: 10, y: 20) {
$0 + $1
}
 

이게 최종 축약형 🎯


8️⃣ multiply 예제 (클로저를 변수에 저장)

 
let multiply = {(val1: Int, val2: Int) -> Int in
return val1 * val2
}
 

사용:

 
multiply(10, 20)
 

즉:

함수처럼 호출 가능

왜냐하면 Swift는

클로저 = 1급 객체

이기 때문


9️⃣ 함수 자체도 클로저처럼 전달 가능

 
result = math(x: 10, y: 20, cal: multiply)
 

함수도 가능:

 
result = math(x: 10, y: 20, cal: add)
 

왜냐하면 Swift에서

함수 타입 == 클로저 타입

이기 때문


🔟 축약 과정 전체 흐름 정리

이 코드가:

 
{ (val1: Int, val2: Int) -> Int in
return val1 + val2
}
 

이렇게 줄어듭니다:

① 반환형 생략

{ (val1: Int, val2: Int) in
 

② 매개변수 이름 생략

{ $0, $1 in
 

③ return 생략

{ $0 + $1 }
 

🎯 시험 핵심 포인트 요약

시험에 거의 반드시 나옵니다:

✔ trailing closure 가능 조건
→ 마지막 매개변수가 클로저일 때

✔ shorthand argument name
→ $0, $1

✔ 단일 표현식 클로저
→ return 생략 가능

✔ Swift에서 함수는 1급 객체
→ 변수 저장 가능 / 전달 가능 / 반환 가능


 

 

 직접 초기하는 방법

class Man{
    var age : Int = 0
    var weight : Double = 0.0
}//오류 나는 이유? 값이 있어야해서

 

 

 

 자동으로 옵셔널 방법

class Man{
    var age : Int?
    var weight : Double?
}//오류 나는 이유? 값이 있어야해서

 

옵셔널 변수는 자동으로 초기값이 없어도 nil 로 들어간다. 

 

 

 

 

생성자를 주는 방법

class Man{
    var age : Int
    var weight : Double
    init(){ //initializer로 초기화
        age = 1
        weight = 3.5
    }
}

객체가 만들어 질 떄마다 자동으로 호출하여 만듦

 

 

https://chatgpt.com/s/t_69c237f3f1b48191baf112d4baaed702

 

 

함수명 오버로딩 설명

ChatGPT가 답변을 듣고, 영감을 얻고, 생산력을 높이는 데 도움을 드립니다.

chatgpt.com

 

 


 

 

 

 

 

 

computed property 사용하는 이유

 

https://chatgpt.com/s/t_69c23963f4d0819190a670582488ae49

 

함수명 오버로딩 설명

ChatGPT가 답변을 듣고, 영감을 얻고, 생산력을 높이는 데 도움을 드립니다.

chatgpt.com

 

 

 

 

 


1. Swift

특징

  • override 키워드 필수
  • 부모 메서드는 기본적으로 virtual 개념 (따로 안 써도 됨)
  • final이면 오버라이드 불가

예시

class Animal {
    func speak() {
        print("동물 소리")
    }
}

class Dog: Animal {
    override func speak() {
        print("멍멍")
    }
}

사용

let d = Dog()
d.speak()  // 멍멍

핵심

  • override 안 쓰면 컴파일 에러

2. Java

특징

  • @Override는 선택이지만 거의 필수처럼 사용
  • 부모 메서드는 기본적으로 오버라이드 가능
  • final이면 불가

예시

class Animal {
    void speak() {
        System.out.println("동물 소리");
    }
}

class Dog extends Animal {
    @Override
    void speak() {
        System.out.println("멍멍");
    }
}

핵심

  • @Override 없어도 동작하지만, 쓰는 게 안전함

3. C++

특징

  • override 키워드는 선택
  • 반드시 부모 함수가 virtual이어야 제대로 동작

예시

#include <iostream>
using namespace std;

class Animal {
public:
    virtual void speak() {
        cout << "동물 소리" << endl;
    }
};

class Dog : public Animal {
public:
    void speak() override {
        cout << "멍멍" << endl;
    }
};

핵심

  • virtual 없으면 다형성 깨짐
  • override는 실수 방지용

4. Python

특징

  • 키워드 없음
  • 그냥 같은 이름으로 재정의하면 됨

예시

class Animal:
    def speak(self):
        print("동물 소리")

class Dog(Animal):
    def speak(self):
        print("멍멍")

핵심

  • 매우 자유롭지만 실수 잡기 어려움

5. JavaScript (ES6 클래스)

특징

  • 키워드 없음
  • 동일 이름 메서드로 덮어쓰기

예시

class Animal {
  speak() {
    console.log("동물 소리");
  }
}

class Dog extends Animal {
  speak() {
    console.log("멍멍");
  }
}

6. C#

특징

  • 부모: virtual
  • 자식: override 필수

예시

class Animal {
    public virtual void Speak() {
        Console.WriteLine("동물 소리");
    }
}

class Dog : Animal {
    public override void Speak() {
        Console.WriteLine("멍멍");
    }
}

핵심

  • Swift랑 비슷하게 override 필수

7. Kotlin

특징

  • 부모: open
  • 자식: override 필수

예시

open class Animal {
    open fun speak() {
        println("동물 소리")
    }
}

class Dog : Animal() {
    override fun speak() {
        println("멍멍")
    }
}

핵심

  • 기본적으로 오버라이드 막혀 있음 → open 필요

8. 정리 비교

언어부모 설정자식 설정특징

Swift 없음 override 필수 안전함
Java 없음 @Override (권장) 유연
C++ virtual override (권장) 실수 많음
Python 없음 없음 가장 자유
JS 없음 없음 간단
C# virtual override 필수 엄격
Kotlin open override 필수 기본 차단

9. 핵심 차이 한 줄 정리

  • Swift / C# / Kotlin → 명시적으로 override 강제
  • Java → 선택적
  • C++ → virtual 있어야 제대로 동작
  • Python / JS → 그냥 덮어쓰기

10. 진짜 핵심 개념

예 (Swift):

let a: Animal = Dog()
a.speak()   // 멍멍 (오버라이드 덕분)

이게 다형성(polymorphism)의 핵심이다.


 

 

모든 프로퍼티를 다 초기화 시키는 생성자를 designated initializer 라고 한다.

 

 


 

extension Double { //extension : 원래 있는 기능을 확장
    var squared : Double {
        return self*self
    }
}
let myValue: Double = 3.5
print(myValue.squared) //과제
print(3.5.squared) //Double형 값에도 .으로 바로 사용 가능
print(myValue.isZero) //instance property, 결과?
0.0.isZero

 

12.25

12.25

false

 


 

(2문제정도 나옴) access modifier

Swift Access Modifier 정리표

접근 제어자접근 가능 범위상속 가능override 가능사용 목적
open 다른 모듈에서도 가능 가능 가능 라이브러리 확장 허용
public 다른 모듈에서도 가능 불가능 불가능 외부 사용만 허용
internal 같은 모듈 내부 가능 가능 기본 설정
fileprivate 같은 파일 내부 가능 가능 파일 단위 공유
private 같은 선언 블록 내부 제한적 제한적 완전 내부 보호

범위 비교 한 줄 요약표

접근 범위는 이렇게 넓어집니다:

private < fileprivate < internal < public < open
 

왼쪽일수록 더 제한적 🔒
오른쪽일수록 더 공개적 🌍


 
 



첫 번째 외부매개변수명만 생략하는, 4번째 방법을 제일 많이 사용한다.

 


1.

func add(x: Int, y: Int) -> Int

함수명: add(x:y:)

 

2. 

func add(first x: Int, second y: Int) -> Int

함수명: add(first:second:)


3.

func add(_ x: Int, _ y: Int) -> Int

함수명: add(_:_) → 외부 매개변수명 없음


4. 

func add(_ x: Int, with y: Int) -> Int

함수명: add(_:with:)


핵심 정리

  • Swift는 외부 매개변수 이름까지 포함해서 함수를 구분한다.
    → 그래서 오버로딩 가능

 

함수 코드

func tableView(_ tableView: UITableView,
               numberOfRowsInSection section: Int) -> Int {
    return items.count
}

1. 함수명 (호출 시 기준)

Swift에서 함수명은 외부 매개변수 라벨까지 포함해서 본다.

그래서 이 함수의 이름은 :

tableView(_:numberOfRowsInSection:)

_는 첫 번째 외부 라벨이 없다는 의미
두 번째는 numberOfRowsInSection


2. 함수 타입 (자료형)

규칙: (매개변수 타입들) -> 반환 타입

(UITableView, Int) -> Int

정리

구분내용

함수명 tableView(_:numberOfRowsInSection:)
함수 타입 (UITableView, Int) -> Int

이해 포인트

  • 함수명 → 외부 라벨 포함
  • 함수 타입 → 타입만, 라벨은 제거

한 줄 요약

이름은 라벨까지, 타입은 타입만 본다

 

 

 


 

 

func print(
    _ items: Any...,
    separator: String = " ",
    terminator: String = "\n"
)

 

 

https://chatgpt.com/s/t_69c2225cb834819193abb9e5f7dbe726

 

함수명 오버로딩 설명

ChatGPT가 답변을 듣고, 영감을 얻고, 생산력을 높이는 데 도움을 드립니다.

chatgpt.com

 


 

 

func up(num: Int) -> Int {
    return num + 1
}
func down(num: Int) -> Int {
    return num - 1
}
let toUp = up // Swift 함수는 일급 객체로, 변수나 상수에 저장할 수 있음
print(up(num: 5))
toUp(10)
// print(up(num:10))
// print(toUp(10)) //주의 : argument label인 (num:) 안 씀
// 함수를 변수에 할당하면 argument label(num:)을 생략해야 함
let toDown = down
print(toDown(20))

 

함수를 어떤 변수에 저장할 수 있지만 그 변수로 함수를 호출할 때는 argument label 을 쓰지 않아도 된다.

 

 


 

 

 

 

colorChangeTimer = Timer.scheduledTimer(withTimeInterval: 1.0, repeats: true) { timer in
    let red = CGFloat(arc4random_uniform(256)) / 255.0
    let green = CGFloat(arc4random_uniform(256)) / 255.0
}

 

 

 

 


 

 

 

자료형

 

 


 

 

 

 

 

후행 클로저를 자동으로 만들려면 파란 부분에서 엔터키를 누르면 자동으로 클로저로 바뀐다.

 

 

 


 

 

옵셔널 변수는 자동으로 초기값이 없어도 nil 로 들어간다. 

 

 

https://chatgpt.com/s/t_69c237f3f1b48191baf112d4baaed702

 

함수명 오버로딩 설명

ChatGPT가 답변을 듣고, 영감을 얻고, 생산력을 높이는 데 도움을 드립니다.

chatgpt.com

 

 

 

 

 

 

computed property 사용하는 이유

 

https://chatgpt.com/s/t_69c23963f4d0819190a670582488ae49

 

함수명 오버로딩 설명

ChatGPT가 답변을 듣고, 영감을 얻고, 생산력을 높이는 데 도움을 드립니다.

chatgpt.com

 

 

 

 

 


1. Swift

특징

  • override 키워드 필수
  • 부모 메서드는 기본적으로 virtual 개념 (따로 안 써도 됨)
  • final이면 오버라이드 불가

예시

class Animal {
    func speak() {
        print("동물 소리")
    }
}

class Dog: Animal {
    override func speak() {
        print("멍멍")
    }
}

사용

let d = Dog()
d.speak()  // 멍멍

핵심

  • override 안 쓰면 컴파일 에러

2. Java

특징

  • @Override는 선택이지만 거의 필수처럼 사용
  • 부모 메서드는 기본적으로 오버라이드 가능
  • final이면 불가

예시

class Animal {
    void speak() {
        System.out.println("동물 소리");
    }
}

class Dog extends Animal {
    @Override
    void speak() {
        System.out.println("멍멍");
    }
}

핵심

  • @Override 없어도 동작하지만, 쓰는 게 안전함

3. C++

특징

  • override 키워드는 선택
  • 반드시 부모 함수가 virtual이어야 제대로 동작

예시

#include <iostream>
using namespace std;

class Animal {
public:
    virtual void speak() {
        cout << "동물 소리" << endl;
    }
};

class Dog : public Animal {
public:
    void speak() override {
        cout << "멍멍" << endl;
    }
};

핵심

  • virtual 없으면 다형성 깨짐
  • override는 실수 방지용

4. Python

특징

  • 키워드 없음
  • 그냥 같은 이름으로 재정의하면 됨

예시

class Animal:
    def speak(self):
        print("동물 소리")

class Dog(Animal):
    def speak(self):
        print("멍멍")

핵심

  • 매우 자유롭지만 실수 잡기 어려움

5. JavaScript (ES6 클래스)

특징

  • 키워드 없음
  • 동일 이름 메서드로 덮어쓰기

예시

class Animal {
  speak() {
    console.log("동물 소리");
  }
}

class Dog extends Animal {
  speak() {
    console.log("멍멍");
  }
}

6. C#

특징

  • 부모: virtual
  • 자식: override 필수

예시

class Animal {
    public virtual void Speak() {
        Console.WriteLine("동물 소리");
    }
}

class Dog : Animal {
    public override void Speak() {
        Console.WriteLine("멍멍");
    }
}

핵심

  • Swift랑 비슷하게 override 필수

7. Kotlin

특징

  • 부모: open
  • 자식: override 필수

예시

open class Animal {
    open fun speak() {
        println("동물 소리")
    }
}

class Dog : Animal() {
    override fun speak() {
        println("멍멍")
    }
}

핵심

  • 기본적으로 오버라이드 막혀 있음 → open 필요

8. 정리 비교

언어부모 설정자식 설정특징

Swift 없음 override 필수 안전함
Java 없음 @Override (권장) 유연
C++ virtual override (권장) 실수 많음
Python 없음 없음 가장 자유
JS 없음 없음 간단
C# virtual override 필수 엄격
Kotlin open override 필수 기본 차단

9. 핵심 차이 한 줄 정리

  • Swift / C# / Kotlin → 명시적으로 override 강제
  • Java → 선택적
  • C++ → virtual 있어야 제대로 동작
  • Python / JS → 그냥 덮어쓰기

10. 진짜 핵심 개념

오버라이드는 단순히 덮어쓰는 게 아니라

“부모 타입으로 다뤄도 자식의 동작이 실행되게 하는 것”

예 (Swift):

let a: Animal = Dog()
a.speak()   // 멍멍 (오버라이드 덕분)

이게 다형성(polymorphism)의 핵심이다.


 

 

모든 프로퍼티를 다 초기화 시키는 생성자를 designated initializer 라고 한다.

 

 


 

extension Double { //extension : 원래 있는 기능을 확장
    var squared : Double {
        return self*self
    }
}
let myValue: Double = 3.5
print(myValue.squared) //과제
print(3.5.squared) //Double형 값에도 .으로 바로 사용 가능
print(myValue.isZero) //instance property, 결과?
0.0.isZero

 

12.25

12.25

false

 


 

access modifier

 

 

 

좋아요공감
공유하기
게시글 관리

 

관련글 더보기