[Python] Pythonic Code

Hyunwoo Lee·2022년 1월 19일
0

일반 코드와의 차이

numbers = ['one', 'two' 'three']
str1 = ''

for number in numbers:
	str1 += number

다음은 파이썬스러운 코드이다.

str2 = ''.join(numbers)

split()

string 값을 기준값으로 나눠서 List 형태로 변환

items = "zero one two three"
item = items.splice() #["zero", "one", "two", "three"]

list comprehension

general code

result1 = []
for i in range(10):
	result1.append(i)

pythonic code

result2 = [i for i in range(10)]

nested loop

word1 = "Hello"
word2 = "World"
result = [i+j for i in word1 for j in word2]
#['HW', 'Ho', 'Hr', ..., 'ol', 'od']

filter

result2 = [i+j for i in word1 for j in word2 if not(i==j)]

result3 = [i+j for i in word1 for j in word2 if not(i==j) else "goood"]

조건문을 넣을 수도 있다.

2 dimentional list

words = 'Hello world to me'.split()
stuff = [[w.upper(), w.lower(), len(w)] for w in words]
# [['HELLO', 'hello', 5], ..., ['ME', 'me', 2]]

2d vs 1d

case_1 = ['a', 'b', 'c']
case_2 = ['c', 'e', 'a']
result = [i+j for i in case_1 for j in case_2]
# [ac ae aa bc... ce ca]
result = [[i+j for i in case_1] for j in case_2]
# [[ac bc cc] [ae be ce] ...]

enumerate & zip

enumerate

  • list의 element를 추출할 때 번호를 붙혀서 추출
  • index와 element를 동시에 알 수 있다.
for i, v in enumerate(['tic', 'tac' 'toe']):
	print(i, v)
# 0 tic
# 1 tac
# 2 toe

zip

여러개의 list를 하나의 list로 묶어준다
` list(zip(list1, list2)) # [('a', '가'), ('b', '나')]

lambda

  • 함수 이름 없이 함수처럼 쓸 수 있는 익명 함수
  • 수학의 람다 대수에서 유래
    (lambda x, y : x + y)(10, 50) # 60
    up_low = lambda x : x.lower() + x.upper()
  • python3 부터는 권장하지 않음 (PEP8)
    - 테스트의 어려움, 어려운 문법, 문서화 docstring 미비, ...
    • 그래도 많이 쓰긴 함

map function

  • 함수의 결과 값을 한번에 list화
ex = [1, 2, 3, 4, 5]
f = lambda x, y: x + y
print(list(map(f, ex, ex))
# [2, 4, 6, 8, 10]

이럴 경우 알아보기 힘들다. 따라서

result = [f(value) for value in ex]

이런 식으로 적는 것이 편하다.

-lambda 대신 일반 함수도 사용 가능하다.

reduce function

  • 자주 쓰진 않지만 대용량의 데이터를 활용할 때 사용한다
from functools import reduce
reduce(lambda x, y: x+y, [1, 2, 3, 4, 5]

lambda, map, reduce는 직관성이 떨어지기에 사용을 권장하지는 않는다.

iterable object

  • sequence형 데이터(리스트, 튜플 등등)은 모두 iterable obj로서 next, iter 기능이 있다.

generator

  • element가 사용되는 시점에 값을 메모리에 반환
  • iterable obj를 특수한 형태로 사용해주는 함수
  • 큰 데이터를 처리할 때 사용
  • 주로 파일 데이터 처리시 사용
  • loop이 중단될 가능성이 있을 때
  • 대기하다가 필요할 때만 값을 반환하기 때문에 메모리 절약 가능
range(1000) # [1, 2, 3, 4, ..., 999] 깂이 한번에 반환됨
def generator_list(value):
  for i in range(value):
      yield i
result = generator_list(1000) 
#아직 result는 1000개의 값이 들어있지 않음
[value for value in generator_list(1000)]
#또는
list(result) 
#이렇게 해야만 1000개의 값이 메모리에 저장됨

다음과 같이 괄호로 감싸 선언도 가능하다

gen_ex = (n*n for n in range(500))

function passing argument

파이썬에는 parameter를 넘겨주는 여러 방법이 있다.

keyword argument

  • 함수에 입력되는 parameter의 변수명을 사용, arguments를 넘김
  • 값을 순서대로 넣지 않아도 됨
def func1(arg1, arg2):
	print(arg1 + arg2)
    
func1(arg2 = "hello", arg1 = "bye")

default argument

  • parameter의 기본값을 사용, 입력하지 않을 경우 기본 값 출력
def func2(arg1, arg2 = "hello"):
	print(arg1 + arg2)
    
func2(bye)
func2("good", "bye")

가변인자 (variable length)

  • prameter의 수가 정해지지 않은 경우
  • tuple 타입으로 전달됨
def func3(*args):
	print(list(args))
    
func3(1, 2, 3, 4)

키워드 가변인자 (keyword variable-length)

  • parameter의 이름을 따로 정하지 않고 입력하는 방법
  • asterisk 두개(**)를 사용하여 함수의 parameter를 표시함
  • 입력된 값은 dict type로 사용 가능
  • 가변인자는 오직 한개만 기존 가변인자 다음에 사용
def func4(**kwargs):
	print(kwargs)
    
func4(first=1, second=4, third=3)

normal parameter, variable, keyword length, variable length 순으로 써야한다.

def func5(one, two=3, *args, **kwargs):
	...
 	...
    
func5(1, 2, 3, 4, 5, first=1, second=3, hello=5)

한번 keyword variable을 쓰면 뒤는 모두 keyword variable이어야 한다.

asterisk

  • 곱하기, 제곱, 가변인자 등에 사용
  • 또는 tuple, dict 등 자료형에 들어가 있는 값을 unpacking
def asterisk_test1(a, *args):#여기서 *은 가변인자를 위한 *
	print(args)
def asterisk_test2(a, args):
	print(args)
	print(*args)
    
asterisk_test1(1, *(2, 3, 4, 5, 6))	# (1, 2, 3, 4, 5, 6)
asterisk_test2(1, (2, 3, 4, 5, 6)) 	# 1, (1, 2, 3, 4, 5, 6)
					# (1, 2, 3, 4, 5, 6)

keyword unpacking

  • dict형식 데이터를 keyword parameter로 변환해줌
def asterisk_test3(a, b, c, d):
	print(a, b, c, d)
data = {'b':1, 'c':2, 'd':3}
asterisk_test(10, **data) # (10, 1, 2, 3)

profile
10분만 쉬어요

0개의 댓글