λ³Έλ¬Έ λ°”λ‘œκ°€κΈ°

πŸ“ 기둝/TIL

[TIL] 20240102

Closure

ν΄λ‘œμ €λŠ” 일정기λŠ₯을 ν•˜λŠ” μ½”λ“œλ₯Ό ν•˜λ‚˜μ˜ λΈ”λ‘μœΌλ‘œ λͺ¨μ•„놓은 것을 λ§ν•©λ‹ˆλ‹€.
μ‹€ν–‰κ°€λŠ₯ν•œ μ½”λ“œλΈ”λŸ­μ΄λΌκ³ λ„ ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

 

ν•¨μˆ˜λ„ ν΄λ‘œμ €μ˜ ν•œ ν˜•νƒœ (ν•¨μˆ˜λŠ” 이름이 μžˆλŠ” ν΄λ‘œμ €)

ν΄λ‘œμ €λΌλŠ” κ°œλ… μ•ˆμ— ν•¨μˆ˜κ°€ ν¬ν•¨λ˜λŠ” 것이라고 ν•  수 μžˆμŠ΅λ‹ˆλ‹€.

→ ν•¨μˆ˜: named Closure , μ΄μ™Έμ˜ ν΄λ‘œμ €λ“€μ€ λ‹€ (unamed) Closure

 

ν΄λ‘œμ €λŠ” μΌκΈ‰κ°μ²΄μ˜ νŠΉμ„±μ„ 가지고 있음

κ·Έλ ‡κΈ° λ•Œλ¬Έμ— λ³€μˆ˜λ‚˜ μƒμˆ˜μ— λŒ€μž…ν•˜κ³ , λ°˜ν™˜(return)κ°€λŠ₯ν•˜λ©° νŒŒλΌλ―Έν„°λ‘œ 받을 수 μžˆλ‹€.

== μ „λ‹¬μΈμž, λ³€μˆ˜, μƒμˆ˜ 등에 μ €μž₯ 및 전달이 κ°€λŠ₯ν•˜λ‹€λŠ” 뜻

ν•¨μˆ˜μ™€ λ‹€λ₯΄κ²Œ μ΄λ¦„μ •μ˜κ°€ ν•„μš”ν•˜μ§€λŠ” μ•Šμ§€λ§Œ, λ§€κ°œλ³€μˆ˜ 전달과 λ°˜ν™˜ 값이 μ‘΄μž¬ν•  수 μžˆλ‹€λŠ” 점이 동일

ν΄λ‘œμ € ν‘œν˜„μ‹

{ (parameters) -> ReturnType in  // closure head
    μ‹€ν–‰μ½”λ“œ(body)  // closure body
}

 

-> 을 μ΄μš©ν•΄ λ°˜ν™˜ νƒ€μž…μ„ λͺ…μ‹œν•©λ‹ˆλ‹€.

ν΄λ‘œμ € ν—€λ“œμ™€ ν΄λ‘œμ € λ°”λ””λ₯Ό κ΅¬λΆ„μ§€μ–΄μ£ΌλŠ” 것이 in ν‚€μ›Œλ“œ!

κΈ°λ³Έ ν΄λ‘œμ €

1️⃣ νŒŒλΌλ―Έν„°μ™€ λ¦¬ν„΄νƒ€μž…μ΄ λ‘˜λ‹€ μ—†λŠ” ν΄λ‘œμ €
2️⃣ νŒŒλΌλ―Έν„°μ™€ λ¦¬ν„΄νƒ€μž…μ΄ μžˆλŠ” ν΄λ‘œμ €

 

1. νŒŒλΌλ―Έν„°μ™€ λ¦¬ν„΄νƒ€μž…μ΄ λ‘˜λ‹€ μ—†λŠ” ν΄λ‘œμ €

ν΄λ‘œμ €λŠ” 일급객체이기 λ•Œλ¬Έμ— μƒμˆ˜μ— ν΄λ‘œμ €λ₯Ό λŒ€μž…ν•  수 μžˆλ‹€.

let closure = { () -> () in
    print("Closure")
}

 

Swiftμ—μ„œ ν•¨μˆ˜λŠ” λ¦¬ν„΄νƒ€μž…μ΄ μ—†μœΌλ©΄ μƒλž΅μ΄ κ°€λŠ₯함. ν΄λ‘œμ €λ„ λ§ˆμ°¬κ°€μ§€λ‘œ μƒλž΅μ΄ κ°€λŠ₯!

근데!!! ν΄λ‘œμ €λŠ” λ¦¬ν„΄νƒ€μž… μžˆμ–΄λ„ μƒλž΅μ΄ κ°€λŠ₯함

μš”κ²ƒμ„ μ•”μ‹œμ  λ°˜ν™˜ ν‘œν˜„μ΄λΌκ³  ν•˜λŠ”λ°, ν΄λ‘œμ €κ°€ λ°˜ν™˜ν•˜λŠ” 값이 μžˆλ‹€λ©΄ ν΄λ‘œμ €μ˜ λ§ˆμ§€λ§‰ μ€„μ˜ 결과값은 return ν‚€μ›Œλ“œλ₯Ό μƒλž΅ν•˜λ”λΌλ„ μ•”μ‹œμ μœΌλ‘œ λ°˜ν™˜κ°’μœΌλ‘œ μ·¨κΈ‰ν•œλ‹€. (μ•„λž˜ μ˜ˆμ‹œ μ½”λ“œμ™€ 같이)

 

result = calculate(a: 10, b: 10) {
     a + b
}

print(result) // 20

 

2. νŒŒλΌλ―Έν„°μ™€ λ¦¬ν„΄νƒ€μž…μ΄ μžˆλŠ” ν΄λ‘œμ €

let closure = { (name: String) -> String in
    return "Hello, \\(name)"
}

 

but μ—¬κΈ°μ„œ ν•œ 가지 μ£Όμ˜ν• μ μ€!!!!! 이 친ꡬ ν˜ΈμΆœν•  λ•Œμž„

 

closure("jane")
closure(name: "jane") // μ΄λ ‡κ²Œ μ“°λ©΄ μ—λŸ¬λ‚©λ‹ˆλ‹€

 

μœ„μ™€ 같이 ν΄λ‘œμ €λ₯Ό ν˜ΈμΆœν• λ•ŒλŠ” argument label을 μ‚¬μš©ν•˜μ§€ μ•ŠλŠ”λ‹€.

‘name’은 였직 parameter name!!

 

βž• κ·Όλ° μš” νŒŒλΌλ―Έν„° λ„€μž„μ΄ λΆˆν•„μš”ν•˜λ‹€λ©΄???

단좕 인자 이름을 ν™œμš©ν•  수 μžˆλ‹€.

단좕 인자 이름은 ν΄λ‘œμ €μ˜ λ§€κ°œλ³€μˆ˜μ˜ μˆœμ„œλŒ€λ‘œ $0, $1, $2...처럼 ν‘œν˜„ (μ•„λž˜ μ½”λ“œμ™€ 같이)

 

result = calculate(a: 10, b: 10) {
     $0 + $1
}

print(result) // 20

⭐️ μΌκΈ‰κ°μ²΄λ‘œμ„œ ν΄λ‘œμ € ⭐️

1️⃣ ν΄λ‘œμ €λ₯Ό λ³€μˆ˜, μƒμˆ˜μ— λŒ€μž…κ°€λŠ₯
2️⃣ ν•¨μˆ˜μ˜ λ°˜ν™˜ νƒ€μž…μœΌλ‘œ ν΄λ‘œμ €λ₯Ό μ‚¬μš© κ°€λŠ₯
3️⃣ ν•¨μˆ˜μ˜ νŒŒλΌλ―Έν„° νƒ€μž…μœΌλ‘œ ν΄λ‘œμ €λ₯Ό 전달 κ°€λŠ₯ (ν•¨μˆ˜μ˜ μ „λ‹¬μΈμžλ‘œ μ‚¬μš©ν•  수 μžˆλ‹€)

 

1. ν΄λ‘œμ €λ₯Ό λ³€μˆ˜, μƒμˆ˜μ— λŒ€μž…κ°€λŠ₯

// ν΄λ‘œμ € μ„ μ–Έκ³Ό λ™μ‹œμ— λŒ€μž…
let closure = { () -> () in
    print("Closure")
}

// μƒˆλ‘œμš΄ λ³€μˆ˜λ‚˜ μƒμˆ˜μ— λŒ€μž…λ„ κ°€λŠ₯ 
let closure2 = closure

 

2. ν•¨μˆ˜μ˜ λ°˜ν™˜ νƒ€μž…μœΌλ‘œ ν΄λ‘œμ €λ₯Ό μ‚¬μš©κ°€λŠ₯

func doSomething() -> () -> () {
}

// μ΄λ ‡κ²Œ ν΄λ‘œμ €λ₯Ό 리턴할 수 μžˆλ‹€
func doSomething() -> () -> () {
    
    return { () -> () in
        print("Hello!")
    }
}

// μ‹€ν–‰
let closure = doSomething()
closure()

 

3. ν•¨μˆ˜μ˜ νŒŒλΌλ―Έν„° νƒ€μž…μœΌλ‘œ ν΄λ‘œμ €λ₯Ό 전달 κ°€λŠ₯

// ν•¨μˆ˜λ₯Ό νŒŒλΌλ―Έν„°λ‘œ μ „λ‹¬λ°›λŠ” doSomethingμ΄λΌλŠ” ν•¨μˆ˜κ°€ 있음
func doSomething(closure: () -> ()) {
    closure()
}

// νŒŒλΌλ―Έν„°λ‘œ μ΄λ ‡κ²Œ ν΄λ‘œμ €λ₯Ό λ„˜κ²¨μ€˜λ„ λœλ‹€
doSomething(closure: { () -> () in
    print("Hello!") // Hello! 
})

 

πŸ”½ ν΄λ‘œμ € 더 μžμ„Ένžˆ μ •λ¦¬ν•œ κΈ€!!!

 

[Swift] ν΄λ‘œμ €(Closure)

μ΅œκ·Όμ— iOS μŠ€ν„°λ”” μΉœκ΅¬λ“€κ³Ό ν•¨κ»˜ ν΄λ‘œμ €μ— λŒ€ν•΄ κ³΅λΆ€ν•΄λ³΄μ•˜λŠ”λ°μš”, λΈ”λ‘œκ·Έμ—λ„ κ·Έ λ‚΄μš©μ„ ν•œλ²ˆ 정리해보렀고 ν•©λ‹ˆλ‹€!😊 데이터 전달, μ„œλ²„ 톡신 λ“± λ‹€μ–‘ν•œ μƒν™©μ—μ„œ μœ μš©ν•˜κ²Œ μ΄μš©κ°€λŠ₯ν•œ 클둜

janechoi.tistory.com

κ³ μ°¨ν•¨μˆ˜

κ³ μ°¨ν•¨μˆ˜λŠ” λ‹€λ₯Έ ν•¨μˆ˜(=ν΄λ‘œμ €)λ₯Ό μ „λ‹¬μΈμžλ‘œ λ°›κ±°λ‚˜ ν•¨μˆ˜(=ν΄λ‘œμ €)λ₯Ό 결과둜 λ°˜ν™˜ν•˜λŠ” ν•¨μˆ˜λ₯Ό λ§ν•©λ‹ˆλ‹€.

(SwiftλŠ” ν•¨μˆ˜λ₯Ό 일급 객체둜 μ·¨κΈ‰ν•˜κΈ° λ•Œλ¬Έμ— ν•¨μˆ˜λ₯Ό λ‹€λ₯Έ ν•¨μˆ˜μ˜ μ „λ‹¬μΈμžλ‘œ μ‚¬μš©ν•˜κ±°λ‚˜ ν•¨μˆ˜λ₯Ό 결과둜 λ°˜ν™˜ν•˜λŠ” 것이 κ°€λŠ₯)

λŒ€ν‘œμ μΈ κ³ μ°¨ν•¨μˆ˜λ‘œ map, filter, reduceκ°€ 있음

 

[Swift] κ³ μ°¨ν•¨μˆ˜ - map, filter, reduce

μ•ˆλ…•ν•˜μ„Έμš” μ œμΈμž…λ‹ˆλ‹€! μ˜€λŠ˜μ€ Swift의 κ³ μ°¨ν•¨μˆ˜ λŒ€ν•΄ μ•Œμ•„λ³΄λ €κ³  ν•©λ‹ˆλ‹€. Swift의 μ—¬λŸ¬κ°€μ§€ κ³ μ°¨ν•¨μˆ˜ 쀑 κ°€μž₯ 자주 쓰이고, μ•Œκ³ λ¦¬μ¦˜ 문제 풀이 μ‹œμ—λ„ μœ μš©ν•˜κ²Œ μ‚¬μš©λ˜λŠ” map, filter, reduce μš” μ„Έκ°€

janechoi.tistory.com

κ³ μ°¨ν•¨μˆ˜ 직접 κ΅¬ν˜„ν•΄λ³΄κΈ°

extension Array {
    
    func myMap<T>(_ transform: (Element) -> T) -> [T] {
        var arr = [T]()
        for i in self {
            arr.append(transform(i))
        }
        return arr
    }
    
    func myFilter(_ transform: (Element) -> Bool) -> [Element] {
        var arr = [Element]()
        for i in self {
            if transform(i) {
                arr.append(i)
            }
        }
        return arr
    }
    
    func myReduce(_ initialResult: Element,
                  _ nextPartialResult: (Element, Element) -> Element) -> Element {
        var result = initialResult
        for i in self {
            result = nextPartialResult(result, i)
        }
        return result
    }
}

let mapResult = [1, 2].myMap{ $0 * 2 }
print("mapResult:", mapResult) // [2, 4]

let filteredArr = [1, 2].myFilter { $0 % 2 == 0 }
print("filteredArr:", filteredArr) // [2]

let sum = [1, 2].myReduce(0) {
    return $0 + $1
}
print("sum:", sum) // 3

 

πŸ”½ Swift κ³ μ°¨ν•¨μˆ˜ λ‚΄λΆ€ κ΅¬ν˜„ ν™•μΈν•˜κΈ°

https://github.com/apple/swift/blob/main/stdlib/public/core/SequenceAlgorithms.swift#L624

 

'πŸ“ 기둝 > TIL' μΉ΄ν…Œκ³ λ¦¬μ˜ λ‹€λ₯Έ κΈ€

[TIL] 20231215  (1) 2023.12.18
[TIL] 20231207  (3) 2023.12.08
[TIL] 20231206  (0) 2023.12.08
[TIL] 20231205  (2) 2023.12.05
[TIL] 20231204  (1) 2023.12.04