티스토리 뷰
파이썬에서 리스트만 잘 다루어도 C나 자바로 프로그래밍하던 것에 비해 훨씬 성과가 좋아짐을 느낀다. 물론 리스트에 관련된 앞의 포스트에서 살펴본 함수나 메소드를 이용해야 진짜 파이썬의 장점을 알 수 있다. 그런데 거기서 한 걸음 크게 올라갈 수 있는 것이 컴프리헨션이다. 파이썬 언어의 창시자인 반 귀도 로썸은 파이썬의 가장 큰 장점으로 컴프리헨션을 들었다고 한다.
컴프리헨션은 특정 성질을 만족하는 값을 반복적으로 생성하여 리스트를 만드는 단축코드라고 볼 수 있다. 우리는 리스트를 만들기 위해 다음과 같은 코드를 자주 만들게 된다.
mylist = []
for x in range(1, 10):
mylist.append(x*x)
이 코드는 1~9까지 수의 제곱을 가지는 리스트를 만든다. 먼저 빈 리스트 이름을 하나 선언하고 거기에 for 루프 반복을 이용해 값을 차례로 하나씩 덧붙인다. 비슷하게 랜덤 수 n개를 만드는 리스트는 다음과 같다.
randlist = []
for x in range(n):
randlist.append(rand.randrange(100))
여기서 rand.randrange(100)은 0~99 사이의 랜덤값을 생성하여 돌려주는 random 모듈의 함수다. 어쨌거나 이 코드는 n개의 랜덤수를 randlist에 넣어준다. 문제는 이런 식으로 리스트를 만들어야 하는 일이 너무 많다는 것이다. 파이썬에서는 많은 것을 리스트로 다루고 리스트에서 다른 리스트를 계산해내는 일이 매우 많다. 이런 코드를 다 일일이 새로 빈 리스트 정의하고 for 루프 돌려서 일일이 append한다면 파이썬 언어의 오늘날의 명성은 없었을 것이다.
컴프리헨션은 이런 코드를 다음과 같이 간략하게 작성하게 해 준다.
mylist = [x*x for x in range(1, 10)]
randlist = [rand.randint(100) for _ in range(n)]
#밑줄 _은 for 문에서 굳이 range의 값을 사용할 필요없을 때 불필요한 변수를 만들지 않고 밑줄로 대치하게 해 준다.
이렇게 한 줄로 새로운 리스트를 만드는 것이 가능하다. mylist의 경우는 1~9의 값을 차례로 제곱한 수열을 가진다. 이것이 빈 리스트에 차례로 제곱한 값을 append하는 것보다 코드가 훨씬 이해하기 쉽다. 실제로 실행의 효율성도 더 좋아진다. 가독성과 성능 효율성이 동시에 좋아질 수 있는 정말 좋은 기능이다.
두 번째 randlist는 주어진 n 값 만큼 반복하여 랜덤한 값을 생성하여 리스트로 가지게 된다. 원하는 개수만큼 어떤 값을 반복하여 생성하는 것이 컴프리헨션의 가장 일반적인 형태이다.
추가로 몇 가지 인상적인 예제를 좀더 살펴보자. 우리는 randlist로부터 다음과 같은 새로운 리스트를 간단히 만들 수 있다. 컴프리헨션에서 뒤에 if 문을 붙여서 원하는 성질을 만족하는 값만 필터링할 수 있는 기능이다.
# randlist에서 3의 배수만 가지는 리스트
multiple3 = [i for i in randlst if i % 3 == 0]
# 3이나 5로 나누어지지 않는 숫자의 리스트
not_divide_3or5 = [i for i in randlst if i % 3 != 0 and i % 5 != 0]
컴프리헨션의 몇가지 기법을 살펴보자. 위의 예에서 우리는 [... for x in ... if ...] 형태를 보았다. 즉 반복하면서 리스트 요소를 생성하는데, if를 만족하는 경우에만 적용하는 것이 가능하다.
또 한가지 기법은 이중 for를 이용하는 것이다. 예를 들어 randlist에 있는 요소를 두 번씩 반복하여 가지는 리스트를 만들고 싶다면? for 루프 안에서 또 반복하는 루프를 돌릴 수 있다.
double_randlist = [x for x in randlist for _ in range(2)]
print(double_randlist)
x에 대해 두 번씩 x 요소를 만들라는 뜻이 된다. 이런 식으로 반복과 조건을 적용하여 리스트를 만들어낼 수 있으므로 컴프리헨션으로 할 수 있는 코드의 범위는 생각보다 굉장히 넓다. 그리고 이것은 두뇌 훈련에도 정말 좋다. 몇 글자 타이핑하지 않고도 엄청난 일을 컴퓨터에게 시킬 수 있으니 성취감도 높다. 파이썬을 배우는 맛이 느껴지는 대목이다.
[연습문제] 다음과 같이 주어진 리스트에서 원하는 값만 가지는 리스트를 만드는 컴프리헨션 코드를 작성해 보자.
(1) 주어진 스트링 리스트 numlist1에서 길이가 3 이상인 것만 가지는 리스트
(2) 주어진 숫자 리스트 numlist1이 주어져 있을 때 그 중에서 짝수만 가지는 리스트
(3) 주어진 숫자 리스트 numlist1이 주어져 있을 때 그 중에서 숫자 3을 포함하지 않은 숫자만 가지는 리스트
(1) [x for x in numlist1 if len(x) >= 3]
(2) [n for n in numlist1 if n % 2 == 0]
(3) [n for n in numlist1 if '3' not in str(n)]
'파이썬 프로그래밍' 카테고리의 다른 글
파이썬 함수 - (2) 빌트인 함수 (0) | 2019.02.20 |
---|---|
파이썬 함수 (0) | 2019.02.18 |
파이썬 리스트 (0) | 2019.01.28 |
파이썬 스트링 (0) | 2019.01.27 |
파이썬 시작하기 (5) - 문장 if와 for (1) | 2019.01.25 |
- Total
- Today
- Yesterday
- sort key
- C++ 클래스
- 자바regex
- rust
- 스트링 +
- max
- follow
- 지연계산
- comparable
- CompareTo
- APPEND
- TypeError
- 동적바인딩
- contains
- contentEquals
- 패턴
- Camel Style
- python exercise
- Lazy evaluation
- ToString
- format
- 콜렉션
- python example
- 스트링
- 이터러블
- zip
- typedef
- Iterator
- 이터레이터
- indexof
일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | 4 | |||
5 | 6 | 7 | 8 | 9 | 10 | 11 |
12 | 13 | 14 | 15 | 16 | 17 | 18 |
19 | 20 | 21 | 22 | 23 | 24 | 25 |
26 | 27 | 28 | 29 | 30 | 31 |