코드로 우주평화

파이썬 매개변수 순서 딱알랴줌! 본문

나는 이렇게 학습한다/Language

파이썬 매개변수 순서 딱알랴줌!

daco2020 2021. 11. 4. 22:34

시작부터 결론 가자!

출처 : https://getkt.com/blog/python-keyword-only-arguments/

함수 매개변수(파라미터) 순서

def func(일반인수, 기본값 지정인수, 가변인수, 키워드인수, 가변 키워드인수):

1순위 : 일반인수 : 일반인수

2순위 : 기본값 지정인수 : 인자에 기본값을 지정해서 따로 인수를 받지 않아도 함수가 받아들이는 인수 ex. a = 0 

3순위 : 가변인수 : 리스트(튜플) 형태의 다수 요소를 가지고 있는 인수

4순위 : 키워드인수 : 키와 값이 1대1 매칭되어 있는 인수, 키가 지정되어 있기 때문에 일반 인수와 달리 위치를 안지켜도 됨

5순위 : 가변 키워드인수 : 키와 값을 가지고 있는 딕셔너리 형태의 다수 요소를 가진 인수

 

왜 이 순서대로 넣어야 하나?

키와 값을 가진 인수라면 위치와 무관하게 해당 키를 찾아갈 수 있지만 일반 인수와, 기본값 지정 인수의 경우 적합한 위치에 넣어야 하기 때문에 맨 앞에 몰아서 위치시켜주어야 한다. 그 중에서도 일반 인수를 기본값 지정 인수보다 앞에 와야 하는 이유는 만약 인풋 인수가 1개인데 파라미터에 기본값 지정 인수가 앞에 오면 들어온 인수가 일반인수 인지 기본값 지정인수인지 알 수 없기 때문이다.

 

무슨 말인지 모를것이니 예제 코드를 봐보자

(default value parameter를 non-default value parameter 앞에 정의 하면 안 되는 이유)

def sample(a,b=0):
  return f"{a}, {b}"

print(sample("good")) 

>>>
good, 0

'a' 라는 일반 인수가 앞에 있는 경우

a는 인수 good 을 인식하여 받아들이고, b 는 기본값이 0으로 지정되어 있으니 따로 인풋을 하지 않아도 0이 출력되는 것을 볼 수 있다

def sample(b=0,a):
  return f"{a}, {b}"

print(sample("good")) 

>>>
  File "main.py", line 1
    def sample(b=0,a):
               ^
SyntaxError: non-default argument follows default argument

b와 a의 순서를 바꾸면 , 위처럼 기본값 지정 인수를 일반 인수보다 뒤로 옲기라는 오류메시지가 나온다. 

인풋하는 good 이 b 에 대한 인수인지, a 에 대한 인수인지 알 수 없기 때문이다!

 

나머지 종류의 인수들도 아래 예제 코드를 통해 살펴보자

 

 

가변인수가 뒤로 가야 하는 이유

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)

>>>
Traceback (most recent call last):
  File "main.py", line 11, in <module>
    func_param_with_var_args("정우성", "01012341234", "seoul", 20)
TypeError: func_param_with_var_args() missing 1 required keyword-only argument: 'age'

가변인수가 일반인수보다 앞에 있으면 인풋 인수 중에 무엇이 가변인수들인지 알 수 없기 때문에 일반인수들보다 뒤로 보내주어야 한다.

def func_param_with_var_args(name, age,*args):
    print("name=",end=""), print(name)
    print("args=",end=""), print(args)
    print("age=",end=""), print(age)

func_param_with_var_args("정우성", 20 , "01012341234", "seoul")
>>>
name=정우성
args=('01012341234', 'seoul')
age=20

수정한 코드를 보면 매개변수(파라미터)의 순서를 바꾸고 거기에 해당하는 인풋인수들의 순서도 변경해 주었다.

이제 정상적으로 출력되는 걸 볼 수 있다.

 

 

가변 키워드 인수가 뒤로 가야 하는 이유

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")

>>>
  File "main.py", line 13
    def func_param_with_kwargs(name, age, **kwargs, address=0):
                                                    ^
SyntaxError: invalid syntax

여기서 address=0 은 기본값이 지정인수이자 키워드 인수이다. 키워드 인수가 가변 키워드인수(**붙은) 보다 앞에 있으면 가변 키워드인수가 일반 키워드 인수도 모두 자기것으로 착각하여 가져가기 때문에 address=0 부분에 에러가 뜨는 것이다. 

def func_param_with_kwargs(name, age, address=0, **kwargs):
  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")
>>> 
name=정우성
age=20
kwargs={'mobile': '01012341234'}
address=seoul

키워드 인수(address)와 가변 키워드인수(**kwarge) 순서를 바꿔주니 정상 작동하는 것을 볼 수 있다. 키워드 인수의 경우 키와 값이 지정되어 있고 매개변수에서도 키를 확인할 수 있기 때문에 일반인수와 기본값 지정인수와는 달리 위치가 달라져도 함수가 키를 찾아 적절한 인수를 받아들일 수 있다.

 

 

 

자 그럼 아래 코드는 무엇이 문제일까?

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")
>>>
  File "main.py", line 21
    def mixed_params(name="아이유", *args, age, **kwargs, address):
                                                       ^
SyntaxError: invalid syntax

첫 번째로, age가 일반인수이므로 매개변수에서 맨 앞으로 위치해야한다.

두 번째로, address는 인풋에서 보면 address="seoul" 처럼 키=값 형태의 키워드인수 이므로 가변 키워드인수 보다 앞에 있어야 한다.

def mixed_params(age, name="아이유", *args, address, **kwargs):
  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")
>>>
name=정우성
args=('01012341234', 'male')
age=20
kwargs={'mobile': '01012341234'}
address=seoul

코드를 수정하니 정상적으로 출력되는 것을 볼 수 있다!

 


 

참고 자료 : https://getkt.com/blog/python-keyword-only-arguments/