[Swift] Higher order function

Lena·2020년 12월 21일
0
post-custom-banner

Higher order function

고차함수란 전달인자로 함수를 전달받거나, 함수 실행의 결과로 함수를 리턴하는 함수이다.

  • Map
  • Filter
  • Reduce
  • CompactMap
  • FlatMap

Map

컨테이너 내부의 기존 데이터를 변형(transform)하여 새로운 컨테이너를 생성한다.

let numbers: [Int] = [0, 1, 2, 3, 4]
var doubledNumbers: [Int]
var strings: [String]

// numbers의 각 요소를 2배하여 새로운 배열 반환
doubledNumbers = numbers.map({ (number: Int) -> Int in
    return number * 2
})

// numbers의 각 요소를 문자열로 변환하여 새로운 배열 반환
strings = numbers.map({ (number: Int) -> String in
    return "\(number)"
})

print(doubledNumbers) // [0, 2, 4, 6, 8]
print(strings) // ["0", "1", "2", "3", "4"]

// 매개변수, 반환 타입, 반환 키워드(return) 생략, 후행 클로저
doubledNumbers = numbers.map { $0 * 2 }
print(doubledNumbers) // [0, 2, 4, 6, 8]

Filter

컨테이너 내부의 값을 걸러서 새로운 컨테이너로 추출한다.

// numbers의 요소 중 짝수를 걸러내어 새로운 배열로 반환
let evenNumbers: [Int] = numbers.filter { (number: Int) -> Bool in
    return number % 2 == 0
}
print(evenNumbers) // [0, 2, 4]

// 매개변수, 반환 타입, 반환 키워드(return) 생략, 후행 클로저
let oddNumbers: [Int] = numbers.filter {
    $0 % 2 != 0
}
print(oddNumbers) // [1, 3]

// ~로 시작하는 이름 찾기
func filterUser(with term: String) {   
    let results: [User] = users.filter {
        let username = $0.username.lowercased()
        return username.hasPrefix(term.lowercased())
    }
    // ...
}

Reduce

컨테이너 내부의 콘텐츠를 하나로 통합한다.

let someNumbers: [Int] = [2, 8, 15]

// 초깃값이 0이고 someNumbers 내부의 모든 값을 더합니다.
let sum: Int = someNumbers.reduce(0, { (first: Int, second: Int) -> Int in
    //print("\(first) + \(second)") //어떻게 동작하는지 확인해보세요
    return first + second
})

print(sum)  // 25

// 초깃값이 0이고 someNumbers 내부의 모든 값을 뺍니다.
var subtract: Int = someNumbers.reduce(0, { (first: Int, second: Int) -> Int in
    //print("\(first) - \(second)") //어떻게 동작하는지 확인해보세요
    return first - second
})

print(subtract) // -25

// 초깃값이 3이고 someNumbers 내부의 모든 값을 더합니다.
let sumFromThree = someNumbers.reduce(3) { $0 + $1 }

print(sumFromThree) // 28

CompactMap

the resulting array does not contain any nil values.

let numbersWithNil = [5, 15, nil, 3, 9, 12, nil, nil, 17, nil]
//let doubledNums = numbersWithNil.map { $0 * 2 } // error
let doubledNums = numbersWithNil.map { $0 != nil ? $0! * 2 : nil }
	
print(doubledNums)
// [Optional(10), Optional(30), nil, Optional(6), Optional(18), Optional(24), nil, nil, Optional(34), nil]
	
let notNilDoubled = numbersWithNil.compactMap { $0 != nil ? $0! * 2 : nil }
print(notNilDoubled) // [10, 30, 6, 18, 24, 34]

Flatmap

flatMap is useful when there are collections inside collections.

let marks = [[3, 4, 5], [2, 5, 3], [1, 2, 2], [5, 5, 4], [3, 5, 3]]

// for-in
var allMarks = [Int]()
for marksArray in marks {
    allMarks += marksArray
}

let allMarks = marks.flatMap { (array) -> [Int] in
    return array
}

// using the shorthand argument
let allMarks = marks.flatMap { $0 }

print(allMarks)
// Prints [3, 4, 5, 2, 5, 3, 1, 2, 2, 5, 5, 4, 3, 5, 3]

References

https://www.boostcourse.org/mo122/lecture/11285
https://www.appcoda.com/higher-order-functions-swift

post-custom-banner

0개의 댓글