접근제한자
클래스, 구조체, 열거형, 포로토콜 등 접근을 제어하는데 사용된다.
Open: 가장 넓은 접근 수준을 가지며, 해당 멤버가 선언된 모듈 외부에서도 상속하고 재정의할 수 있다.
Public: 해당 멤버가 선언된 모듈은 외부에서도 접근할 수 있지만, 재정의는 할 수 없다. 일반적으로 프레임워크의 API 로 공개될 때 사용한다.
Internal : 기본 접근 수준이며 동일한 모듈 내에서만 접근이 가능하다.
File-private: 같은 소스 파일 내에서만 접근할 수 있습니다. 다른 소스 파일에서는 접근할 수 없습니다.
Private: 가장 제한적인 접근 수준을 가지며, 같은 선언 블록내에서만 접근할 수 있다.
이러한 접근 제한자는 코드의 가시성과 모듈간의 의존성을 관리하고 코드의 안전성과 유지 보수성을 높이는데 도움이 된다. 올바른 접근 제한자를 선택하면 다른 개발자들이 해당 코드를 사용할 때 예상치 못한 문제를 피할 수 있으며, 코드를 더욱 안전하고 읽기 쉽게 만들 수 있다.
mutating
mutating은 구조체나 열거형 내부에서 해당 인스턴스를 변경할 수 있도록 허용하는 키워드이다.
일반적으로 구조체나 열거형은 값 타입으로 메서드 내 인스턴스 속성을 변경할 수 없다. 그러나 특정 경우에는 인스턴스의 속성을 변경해야하는 경우가 있는데 이럴때 mutating 을 사용하여 해당 인스턴스의 속성을 변경할 수 있다.
struct Point {
var x = 0.0
var y = 0.0
mutating func moveBy(x deltaX: Double, y deltaY: Double) {
x += deltaX
y += deltaY
}
}
//출력값
var point = Point(x: 1.0, y: 2.0)
point.moveBy(x: 2.0, y: 3.0)
print(point) // 출력 (x: 3.0, y: 5.0)
클로저 (Closure)
클로저는 코드 블록이고 이 코드 블록은 다른 곳에서 사용할 수 있는 독립적인 기능을 담고 있다.
우리는 함수를 변수에 할당하거나 함수의 인자로 전달할 수 있는데, 클로저 역시 이와 같은 방식으로 사용할 수 있다.
간단히 말해 클로저는 코드 조각이며, 이 코드 조각을 특정 상황에서 실행할 수 있습니다.
예를 들어 정렬 기능을 수행하는 함수를 작성할 때 우리는 비교하는 방법을 지정해야합니다. 클로저는 이러한 비교 기능을 간단하게 작성 할 수 있도록 도와줍니다.
클로저는 중괄호로 둘러싸여 있고, 중괄호 안에 매개변수 목록과 실행 코드가 포함됩니다.
{ (parameters) -> ReturnType in
statements
}
여기서 parameters 는 클로저가 사용할 매개변수를 나타내며, ReturnType 은 클로저가 반환할 값의 타입을 나타낸다. in 키워드는 매개변수와 반환 타입을 클로저의 본문으로부터 분리한다.
예를 들어 숫자를 두개 받아서 더하는 클로저는 아래와 같이 표현할 수 있다.
let addClosure = { (a: Int, b: Int) -> Int in
return a + b
}
이제 이 클로저를 사용하여 두 숫자를 더할 수 있다.
let result = addClosure(10, 20) // result 는 30
클로저는 이와 같이 코드를 간결하게 만들고 함수형 프로그래밍 패러다임을 지원하는 강력한 도구
주로 함수의 매개변수로 전달되거나, 함수의 반환 값으로 사용되며, 주변 환경을 캡처하여 실행될 수 있다.
Closure 캡처
값 캡처는 주변 값을 복사하여 사용하고, 참조 캡처는 주변의 객체에 대한 참조를 유지하며 사용합니다. 값 캡처는 값을 복사하기 때문에 클로저가 만들어진 시점의 값을 유지하고, 참조 캡처는 주변의 객체에 대한 참조를 유지하기 때문에 해당 객체의 변경사항이 반영됩니다.
값 캡쳐(Value Capture)
- 값 캡처는 클로저가 주변에 있는 값을 캡처할때 해당 값의 복사본을 저장합니다.
- 클로저가 생성될 때 주변의 값은 복사되어 클로저 내부에서 사용됩니다.
- 이후에 값이 변경되더라도 클로저는 복사된 값을 그대로 유지합니다.
- 주로 값형식(구초제, 열거형)의 인스턴스를 캡처할 때 발생합니다.
- 값 캡처는 주변의 값을 캡처한 시점의 값으로 사용합니다.
func makeIncrementer(startingValue: Int) -> () -> Int {
var value = startingValue // 외부에서 전달된 값 캡처 (값만 가져온다 )
let incrementer: () -> Int = {
value += 1 // 클로저가 캡처한 값 사용
return value
}
return incrementer
}
참조 캡처(Reference Capture)
- 참조 캡처는 클로저가 주변에 있는 참조를 캡처합니다.
- 캡처된 참조는 주변의 객체를 가리키며, 해당 객체에 대한 변경사항은 클로저에서도 반영된다.
- 주로 참조형식(클래스, 인스턴스 등)의 인스턴스를 캡처할 때 발생한다.
- 참조 캡처는 주변의 값을 ‘실제 참조하는 객체’로 사용한다.
class Person {
var name: String
init(name: String) {
self.name = name
}
}
var person = Person(name: "Alice")
let printName: () -> Void = {
print(person.name) //클로저가 캡처한 참조 사용
}
person.name = "Bob"
printName() // "Bob"
위 예시에서 printName 클로저는 person 객체의 name 속성을 캡처합니다. 이후 person 객체의 name 이 변경되어도 클로저는 캡처한 참조를 유지하며 해당 객체의 변경사항이 반영된다.
Closure 매개변수 축약 사용
정렬
let numbers = [10, 5, 8, 2, 7]
//오름차순 정렬
let ascending = numbers.sorted { $0 < $1 }
//내림차순 정렬
let descending = numbers.sorted { $0 > $1 }
필터링
let numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
//짝수만 필터링
let evens = numbers.filter { $0 % 2 == 0 }
//홀수만 필터링
let odds = numbers.filter { $0 % 2 != 0 }
맵핑
let numbers = [1, 2, 3, 4, 5]
// 각 요소에 2를 곱한 결과 배열 생성
let doubled = numbers.map { $0 * 2 }
// 각 요소에 1을 더한 결과 배열 생성
let plus = numbers.map { $0 + 1 }
고차함수
map 함수
map 함수는 배열 또는 컬렉션의 각 요소에 대해 동일한 작업을 수행하고 그 결과를 새로운 배열로 반환하는 고차함수.
각 요소에 함수를 적용하여 변환된 값으로 이루어진 새로운 배열을 생성한다.
let numbers = [1, 2, 3, 4, 5]
let squaredNumbers = numbers.map { $0 * $0 }
print(squaredNumbers) // 출력 : [1, 4 ,9, 16, 25]
예제는 map 함수를 사용하여 numbers 배열의 각 요소를 제곱, 새로운 배열인 squaredNumbers 를 생성했습니다. 클로저 { $0 * $0 } 은 각 요소를 제곱하는 작업
map 함수는 배열 뿐 만 아니라 다양한 컬렉션 타입에서도 사용 가능하며, 각 요소에 대해 동일한 변환 작업을 수행하는데 유용하다.
filter 함수
filter 함수는 배열이나 컬렉션에서 주어진 조건을 만족하는 요소들만 걸러내어 새로운 배열을 반환하는 고차함수이다. 주어진 조건에 따라 요소를 걸러내는데 사용
let numbers = [1, 2, 3, 4, 5]
let evenNumbers = numbers.filter { $0 % 2 == 0 }
print(evenNumbers) // [2 , 4]
예제는 filter 함수를 사용하여 numbers 배열에서 짝수만을 걸러내어 새로운 배열을 생성했습니다. 클로저 { $0 % 2 == 0 } 는 각 요소가 짝수인지 여부를 판별하는 조건을 나타낸다.
filter 함수를 사용하면 특정 조건에 맞는 요소들을 간편하게 걸러낼 수 있으며, 그 결과로 조건을 만족하는 요소로 이루어진 새로운 배열을 얻을 수 있다.
reduce 함수
reduce 함수는 컬렉션(배열 , 딕셔너리 등) 의 모든 요소를 하나의 값으로 결함하는 고차 함수이다. 조어진 초기값과 클로저를 사용하여 컬렉션의 요소를 순회하면서 값을 누적시키고, 최종적으로 하나의 값으로 반환한다.
let numbers = [1, 2, 3, 4, 5]
let sum = numbers.reduce(0) { $0 + $1 }
print(sum) // 15
let numbers2 = [1, 2, 3, 4, 5, 6, 7]
let sum2 = numbers2.reduce(0, +)
print(sum2) // 28
예제와 같이 reduce 함수의 경우, 결과적으로 모든 요소를 더한 총합이 출력된다.
'◽️ Programming > T I L' 카테고리의 다른 글
Swift TIL (제네릭 , 비동기와 네트워킹 , DispatchQueue ) (0) | 2024.03.13 |
---|---|
Swift TIL ( 예외처리 , ARC , 프로토콜 , Extension) (0) | 2024.03.12 |
프로퍼티 옵저버 (didSet , willSet) , 타입 캐스팅 (is , as) (0) | 2024.03.10 |
델리게이트 패턴 , 텍스트 필드 (0) | 2024.03.07 |
Swift (옵셔널 체이닝, Queue , Stack , Set , Overloading) (2) | 2024.03.06 |