파이썬은 람다를 통해서 이름이 없는 간한단 함수를 만들 수 있다.
보통 def
를 사용해서 함수를 만들게 되는데 이때 함수 객체는 메모리에 올라가서 자신이 호출되기를 기다린다. 만약 이 함수가 간단하게 사용되고 마는 함수라면 메모리가 낭비된다.
요약하면 람다함수의 장점은 코드의 간결함, 메모리의 절약이다.
얼마 전에 LeetCode에서 937. Reorder Log Files라는 문제를 풀면서 람다를 사용하게 됐는데, 그 후에 람다의 사용법에 대해서 공부 했다.
이번 포스팅은 람다 함수의 간단한 예, map, reduce, filter 함수에서 람다의 사용법, key와 람다를 사용한 정렬에 대해서 정리한다.
lambda 매개변수 : 결과
람다 함수의 문법이다.
def
를 사용한 함수와 람다 함수를 비교해보면
def plus(x, y):
return x+y
print(plus(1, 2))
# 3
이 함수를 lambda로 표현하면
print((lambda x,y: x+y)(1, 2))
# 3
map(함수, 리스트)
map()은 함수와 리스트를 인자로 받고, 리스트의 각 원소에 함수를 적용시킨 새로운 리스트를 반환한다.
각 원소에 제곱하기
nums = [1, 2, 3, 4, 5]
# 각 원소에 제곱을 한다.
new_nums = list(map(lambda x: x**2, nums))
# 1, 4, 9, 16, 25
print(new_nums)
reduce(집계함수, 순회 가능한 데이터)
reduce()의 집계함수에서 인자는 2개를 받아야 한다. 첫 번째 인자는 누적자(함수 실행부터 종료까지 재사용되는 값)이고, 두 번째 인자는 현재값(데이터를 순회하면서 계속 바뀌는 값)이다.
3번째 인자로 누적자를 초기화하는 값을 넣을 수 있다.
각 원소를 누적해서 모두 더하기
nums = [1, 2, 3, 4, 5]
# nums를 모두 더한다
sum = reduce(lambda acc, cur: acc+cur, nums, 0)
# 15
print(sum)
filter(함수, 리스트)
filter()는 리스트의 각 요소들을 함수에 적용하고, 결과가 참인 값들로 새로운 리스트를 반환한다.
리스트의 원소중 짝수들만 반환하기
nums = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
# nums 중에 짝수만 반환
even = list(filter(lambda x: x % 2 == 0, nums))
# [2, 4, 6, 8, 10]
print(even)
코딩 문제를 풀다보면 리스트 안에 리스트가 들어있는 경우를 정렬하는 문제를 만나곤 한다.
ex) [['신라면', 1200], ['너구리', 1500], ['진라면', 1100]]
이런 경우에 key와 lambda를 사용하면 쉽게 정렬할 수 있다.
일반적인 정렬은 sorted()
또는 sort()
를 사용한다.
인자 없이 sorted()
만 사용하면 리스트의 각 요소의 순서대로 정렬한다.
일반적인 정렬
product = [
['신라면', 1200],
['너구리', 1500],
['진라면', 1100],
['불닭볶음면', 1600],
['삼양라면', 1100],
['안성탕면', 1200]
]
# [['너구리', 1500], ['불닭볶음면', 1600], ['삼양라면', 1100], ['신라면', 1200], ['안성탕면', 1200], ['진라면', 1100]]
print(sorted(product))
각 리스트는 ['상품명', 가격]
으로 이루어져 있다.
이 리스트를 상품명과 가격 중에 하나의 요소를 기준으로 정렬하려면 key
를 사용할 수 있다. 가격을 기준으로 정렬해보자.
가격을 기준으로 정렬
product = [
['신라면', 1200],
['너구리', 1500],
['진라면', 1100],
['불닭볶음면', 1600],
['삼양라면', 1100],
['안성탕면', 1200]
]
# [['진라면', 1100], ['삼양라면', 1100], ['신라면', 1200], ['안성탕면', 1200], ['너구리', 1500], ['불닭볶음면', 1600]]
print(sorted(product, key=lambda x: x[1]))
여러개의 key로 정렬을 할 수도 있다.
key에서 key=lambda x: (x[1], x[0])
이런 식으로 인자를 여러개 사용할 수 있다. 예시 데이터인 product
에서 사용해보자.
가격과 상품명을 기준으로 정렬
product = [
['신라면', 1200],
['너구리', 1500],
['진라면', 1100],
['불닭볶음면', 1600],
['삼양라면', 1100],
['안성탕면', 1200]
]
# [['삼양라면', 1100], ['진라면', 1100], ['신라면', 1200], ['안성탕면', 1200], ['너구리', 1500], ['불닭볶음면', 1600]]
print(sorted(product, key=lambda x: (x[1], x[0])))
key를 한 개만 사용했을 때는 같은 가격인 상품들이 어떤 기준으로 정렬되는지 기준이 없었다. 그래서 삼양라면, 진라면, 신라면, 안성탕면과 같이 가격이 같은 상품들은 정렬 상태가 다르다.
여기서 key에 x[0]
, 즉 상품명을 추가해 준다면 가격이 같은 상품들은 상품명으로 다시 정렬이 된다. 결과를 보면 진라면과 삼양라면의 순서가 바뀐 것을 볼 수 있다.
참고
- map, reduce, filter 함수에서 람다 사용: https://wikidocs.net/64
- key를 여러 개 사용한다면?: https://dailyheumsi.tistory.com/67