Python/2.7 information

Iterator, Generator, Decorator

qkqhxla1 2016. 6. 24. 15:14

예전에 참고하라고 링크를 블로그에 올리긴 했는데...(올려놓기만 하고 자세히 들여다보지는 않았다.) 이터레이터는 뭔지 알겠는데 데코레이터와 제너레이터의 개념을 잘 모르겠어서 좋은 블로그를 보고 정리했다.


이터레이터, 제너레이터 참고 : http://friberry.com/?p=254

데코레이터 참고 : http://ravenkyu.github.io/python_investigation/2015/09/07/decorator/



이터레이터.

이터레이터가 뭔지 쓰려다가 말로 표현을 못 하겠어서 예시를 찾아봤다.

간단한건데 여기 블로그(c로 설명됨)처럼 반복적으로 처리하는 것을 말한다. 이터레이터에 관한 설명은 저 블로그보다는 자바나 c++(을 아는 사람은)관련해서 같이 참고하면 이해하기가 조금 더 편할것 같다.

c++관련 : http://kks227.blog.me/60208809639


for 반복문같은 경우 for i in ~~처럼 쓰는데 단순 문법이 저렇다.. 가 아니라 ~~부분에는 이터러블한 또는 몇몇 객체 같은 것들을 사용 가능하다. 등등을 알아두면 코드 짤대 좋을것 같다. 내부 동작을 이해하는데 도움을 준다고 해야 하나.. 사소한거지만 이런거 알아두면 코드 짤때 더 많이 방법론이 생각나는것 같다.


이터레이터의 활용. 아래는 위의 이터레이터 참고 블로그(http://friberry.com/?p=254)의 일부 내용이 너무 좋아서 통째로 가져왔다.(문제있을시 지우겠습니다. 댓글남겨주세요.)




제너레이터.

피보나치 수열을 제너레이터로 표현한 건데 일반적 구현인 재귀로 구현된것과 비교하면서 보자. (사실 이 제너레이터때문에 글을 씀)

# -*- encoding: cp949 -*-
def fibonacci(i): #재귀를 이용
    if i<=1:
        return 1
    else:
        return fibonacci(i-1)+fibonacci(i-2)

def g_fibonacci(n): #제너레이터를 이용.
    """Fibonacci numbers generator, first n"""
    a, b, counter = 0, 1, 0
    while True:
        if (counter > n): 
            return
        yield a
        a, b = b, a + b
        counter += 1
 
 
f = g_fibonacci(5)
for x in f:
    print(x)  # 0, 1, 1, 2, 3, 5

제너레이터 함수는 yield라는걸 쓰는데 동작을 살펴보면 일반 함수는 return시 그냥 리턴하고 함수 자체를 끝낸다. 그런데 yield는 해당 값을 리턴하고, 함수는 계속 도는 그런 느낌??인것 같다.

여기도 참고 : http://anandology.com/python-practice-book/iterators.html


제너레이터 또한 이터레이터라고 한다.



데코레이터.

위에 적었듯이 http://ravenkyu.github.io/python_investigation/2015/09/07/decorator/ 를 참고했다.

함수 위에 @로 시작하는게 있는게 데코레이터다. 이거 바로 이전글에 데코레이터 예제가 하나 있다.

(실행하려면 https://pypi.python.org/pypi/singledispatch#downloads 모듈 다운로드가 필요하다.)

# -*- encoding: cp949 -*-
from singledispatch import singledispatch
@singledispatch
def fun(arg, verbose=False):
    if verbose:
        print("Let me just say,")
    print(arg)

@fun.register(int)
def _(arg, verbose=False):
    if verbose:
        print("Strength in numbers, eh?")
    print(arg)

@fun.register(list)
def _(arg, verbose=False):
    if verbose:
        print("Enumerate this:")
    for i, elem in enumerate(arg):
        print(i, elem)

fun(10)
fun(['rara','roro'])

지금 다시 앞의글을 읽어보니 앞의 글 자체가 데코레이터를 사용하기에 좋은 예제이다. 그리고 파이썬에서의 함수 오버로딩 구현시 데코레이터를 이용하면 되는 경우가 많을 것 같다.


추가.

요 링크도 좋다 : http://thecodeship.com/patterns/guide-to-python-function-decorators/

'Python > 2.7 information' 카테고리의 다른 글

dict과 list에서 어떤 값을 찾을 경우.  (0) 2016.08.08
in operator 탐구.  (0) 2016.06.30
함수 리팩토링 관련 모듈들.  (0) 2016.06.23
raw 소켓 파악하기 2.  (0) 2016.03.07
raw 소켓 파악하기 1.  (0) 2016.03.07