[TIL] Python - 함수 (Function) (1)

Hailee·2020년 11월 20일
0

[ TIL ]

목록 보기
8/40
post-thumbnail

0. 함수

함수를 사용하는 이유?

  1. 반복되어 계속 사용되는 코드들을 함수로 정의하여 효과적으로 사용
  2. 함수로 정리해서 코드의 가독성 향상

함수의 개념은 간단하다.
input이 있고 output이 있는 간단한 구조!

def 함수명(parameter):
    문장1
    문장2
    ...
    문장N
    [return 리턴값]
  • parameter와 return은 optional입니다.
    : input parameter가 없는 함수도 있고, 리턴값이 없는 함수가 있을수도 있기 때문
  • return값은 함수 -> 해당 함수를 호출한 주체(invoker) 에게 결과값(output) 을 보내주는 것!

예를 들어, 어떠한 수가 prime number(소수)인지 계산하는 로직을 구현한다면?

소수 : 1과 자기자신 이외에 나누어 떨어지는 수가 없는 것
n = 11


# 1 혹은 그 이하이면 소수가 아니다 
if (n <= 1): 
    return False


# 2 와 3은 소수 이다
if (n <= 3): 
    return True


# 2 나 3으로 나누어 떨이지면 소수가 아니다
if (n % 2 == 0 or n % 3 == 0): 
    return False


i = 5
while(i * i <= n): 
    if (n % i == 0 or n % (i + 2) == 0) : 
        return False
    i = i + 6


return True

이러한 소수 계산을 반복하는 코드를 여러번 사용하면
가독성이 현저히 떨어지게 된다.
그래서! 이를 함수로 정의한 후 호출하기만 하는 형태로 바꿔주자

이제 원하는 값을 parameter로 넘겨주어 호출하면 되는 것!

is_eleven_prime = is_prime(11)
print(f"11 is prime? {is_eleven_prime}")


is_ten_prime = is_prime(10)
print(f"10 is prime? {is_ten_prime}")
  • 함수를 사용하면 좋은 점?
    : 코드를 반복 구현하는 일이 감소
    👉🏻 코드 양 감소
    : 함수 이름 자체가 코드 기능 설명
    👉🏻 코드에 대한 이해 높아져서 가독성 증가

1. 함수 정의할 때 유의할 점

1-1. keyword Arguments

👇🏻 Positional Arguments (함수의 기본적인 형태!)
: 순서대로 값이 parameter로 함수에 전해지는 경우

but 위의 경우처럼 순서에 맞추어서 parameter 값을 전해주지 않는 방법도 있다.

👇🏻 Keyword Arguments
: 순서 대신, parameter 이름으로 맞추어서 값을 전해준다.
: 이 방식으로 parameter 값을 전해주면 실제 순서가 바뀌어도 상관이 없다.

이렇게 keyword arguments를 사용하면 좋은점은?
1. 세팅된 parameter의 순서가 바뀌어도 상관이 없다.
: 실수로 값을 바뀌어 넘겨도 parameter에 맞추어서 값을 함수에 넘기기 때문
2. 가독성이 높아진다.
: 어떠한 값을 넘기는건지 명확하게 알 수 있기 때문!

1-2. Mixing positional arguments and keyword arguments

👉🏻 Mixing Both!

  • Positional Arguments + Keyword Arguments
    : 순서 맞추어 넘기기 + parameter명 지정하여 넘기기

주의할 점은 Positional Arguments 부분의 순서 지켜줘야 한다는 것!

def love_you(my_name, your_name): 
   print(f"{my_name} loves {your_name}") 
   
   love_you(your_name = "아이유", "정우성")


> Traceback (most recent call last):
    File "python", line 1
SyntaxError: positional argument follows keyword argument

이렇게 함수를 호출하면 에러가 난다. Why?

  • Keyword Argument가 Positional Argument보다 더 앞으로 위치되어 함수가 호출되었기 때문!
  • 순서를 지켜주지 않으면 에러가 난다는거! 🥺

1-3. Parameter Default Value


👉🏻 Default Value!

  • 함수의 parameter에 default 값을 정의해 줄 수도 있다.
    : default 값이 정의된 parameter는 함수 호출시 값을 넘기지 않아도 된다.
    (자동으로 default 값이 넘겨짐)

조심할 점은 default 값이 정의된 parameterdefault 값이 정의되지 않은 parameter보다 먼저 위치해 있으면 안된다는 거!
default value parameter를 먼저 선언하면 syntax error남!

(Syntax Error[구문 오류] : 문자열, 코드블록 구문 속의 오류 )

2. 에러로 공부하기

2-1. 위치 인수(positional arguments)와 가변인수(variable length arguments)

1) 가변인수 *args (variable length arguments)

  • args로 쓸 뿐, amy, *pypy 등 자유롭게 지정 가능
  • 복수의 일반 인자를 사용자에게 입력받아서 사용할 때 쓰임
    (정해지지 않은 수의 일반 인자)
    ( -> 여러개의 인자를 받은 경우, 함수 내부에서는 튜플로 받은 것처럼 인식)

*args를 사용할 때 주의할 점

  • 예시
def func_param_with_var_args(name, *args, age):
    print("name=",end=""), print(name)
    print("args=",end=""), print(args)
    print("age=",end=""), print(age)
-
func_param_with_var_args("정우성", "01012341234", "seoul", 20)
  • 에러

원인은 함수 선언부!
*args는 사용자가 몇개의 인수를 입력할지 모르는 상황 (하나의 parameter 혹은 튜플)이므로
마지막에 *args를 입력해 주는 것이 좋다.

** 구글링해보니 함수는 첫 선언부가 파라미터 정의에 민감하므로
기본 형식(parameter를 지정해주는 것) 이외의 경우는 무조건 마지막에 입력해주는것이 나을 듯!

2-2. 가변 키워드 인수 (variable length keyword arguments)

가변 키워드 인수 **kwargs (keyword arguments)

  • 자유롭게 지정 가능
  • *args와 달리, 키워드로 이루어진 복수의 인자를 받음
    : 정해지지 않은 수의 키워드로 이루어진 인자
  • 예시
def func_param_with_kwargs(name, age, **kwargs, address=0):
    print("name=",end=""), print(name)
    print("age=",end=""), print(age)
    print("kwargs=",end=""), print(kwargs)
    print("address=",end=""), print(address)
-
func_param_with_kwargs("정우성", "20", mobile="01012341234", address="seoul")

-에러

invalid syntax 구문 에러가 뜬다! 뭔가 맞지 않는다는 소리인데...

원인은 역시나 함수 선언부!
address=0 이라는 default 값이 선언되어있는 parameter 뒤로
가변 키워드 인수를 옮겨주면 정상적으로 함수가 실행되었다. 👇🏻

2-3. 위치 인수와 키워드 가변 키워드 인수 (variable length keyword arguments)

가변인수 + 가변키워드 인수 동시에 사용하기!

  • 예시
def mixed_params(name="아이유", *args, age, **kwargs, address):
    print("name=",end=""), print(name)
    print("args=",end=""), print(args)
    print("age=",end=""), print(age)
    print("kwargs=",end=""), print(kwargs)
    print("address=",end=""), print(address)
mixed_params(20, "정우성", "01012341234", "male" ,mobile="01012341234", address="seoul")
  • 에러

예상가는 원인👇🏻

  1. Keyword Argument가 Positional Argument보다 먼저 나오면 안되는데 제일 먼저 나와있음
  2. 가변인수, 가변키워드인수가 선언부 중간중간에 껴있음
  3. 이미 함수 선언부에 address parameter가 있는데 호출 시에 default value가 선언된 parameter를 입력해둠
    (default 값이 정의된 parameter가 default 값이 정의되지 않은 parameter보다 먼저 위치해 있으면 안됨)


👆🏻 선언부의 parameter 순서들을 바꾸어 보니
address가 multiple values라고 하는걸 보니
예상과 같이 address가 문제인 것 같고...


👆🏻 positional argument follows keyword argument....
위치 인수가 키워드 인수 뒤에 나와서 그렇다고 하는 것 같은데..
(위에서 언급했던 것처럼 Keyword Argument가 Positional Argument보다 더 앞으로 위치되어 함수가 호출되면 에러가 난다)


👆🏻 드디어 성공!!!
positional argument를 앞에 두고, keyword argument를 뒤로 이동했다.
구글링해보니, keyword-only arguments는 특수 인자값으로, *args보다 뒤에 위치해야 한다.

에러 원인 정리

def mixed_params(name="아이유", *args, age, **kwargs, address):
    print("name=",end=""), print(name)
    print("args=",end=""), print(args)
    print("age=",end=""), print(age)
    print("kwargs=",end=""), print(kwargs)
    print("address=",end=""), print(address)
mixed_params(20, "정우성", "01012341234", "male" ,mobile="01012341234", address="seoul")
  1. 가변 인수 *args가 일반 인수 (age, address)보다 뒤에 위치함
    : 일반 인수가 더 앞에 위치해야 함
  2. keyword 가변 인수 **kwargs도 일반 인수보다 앞에 위치함
    : keyword 가변 인수는 가변인수보다도 더 뒤에 위치해야함
  3. name="아이유"는 default 인수인데 맨 앞에 위치함
    : default값 인자는 positional argument 뒤에 위치해야 함 (?)
  4. keyword-only arguments는 특수인자값인데 앞에 위치함
    : *args보다 뒤에 위치해야 함

arguments의 절대적인 순서 & 규칙(함수 선언부)

  1. 일반 positional 인자
  2. default 인자 (이미 값 지정된 인자)
  3. 가변 인자 (*args)
  4. keyword-only 인자
  5. default keyword-only 인자

📖 references
개미님의 브런치 글: https://brunch.co.kr/@princox/180
args와 kwargs 정리해주신 또 다른 분 블로그: https://m.blog.naver.com/PostView.nhn?blogId=wideeyed&logNo=221455090671&proxyReferer=https:%2F%2Fwww.google.com%2F
Alex velog :
https://velog.io/@ifyouseeksoomi/Backend-Python-가변-인수args와-키워드-인수kwargs
(당연히) 점프 투 파이썬: https://wikidocs.net/book/1
https://getkt.com/blog/python-keyword-only-arguments/

profile
웹 개발 🐷😎👊🏻🔥

0개의 댓글