일반적으로 함수는 코드 맨 위에 정의해준다.
- 파이썬의 함수정의
형식 ) def 함수이름 (매개변수): return 반환값
- 파이썬의 함수호출
형식 ) 함수이름(인자값)
* 함수 정의, 호출 예제
def Input (수1,수2):
while(True):
수1 = int(input('수1입력:'))
수2 = int(input('수2입력:'))
break
return 수1,수2
수1 ,수2 = 0 , 0
수1,수2 = Input(수1,수2) # 함수호출하고return값으로돌려받을매개변수 = 함수(함수호출할때넘겨줄매개변수)
print(수1,수2)
파이썬은 함수리턴값 두개 이상으로 줄 수 있다. (무조건 튜플형으로 반환함)
형식 ) return a , b ( , 콘마를 사용하여 튜플형으로 반환 함)
* 함수리턴 2개 이상 예제
def twoReturn (a,b):
return a+b , a-b
print(twoReturn(20,10))
print(type(twoReturn(20,10)))
인자값으로 넘어온 값이 없어도 지정한 default값으로 넘어오게 설정한다. 기본적으로 default 매개변수는 맨뒤에 작성한다.
형식 ) def 함수이름 (매개변수명=디폴트값)
* default 매개변수 예제
def func (a,b=10):
if b == 10 :
print('디폴트 작동')
return
else:
print(a,b)
return
func(50)
func(50,90)
def func(num = 10):
print(num)
func(20)을 하면 20이 전달된다.(키워드인자를 위치인자처럼 인식) 하지만 func()로 매개변수를 주지 않을 시엔 기본값인 10이 들어간다.
* default 매개변수가 앞에 오면 syntax error
def func(a=10,b):
print("문법오류..실행자체가 안됨")
이유는 파이썬의 함수는 조직되어 있기 때문이다. 파이썬의 인자는 종류가 많고 우선순위를 가진다. 엄격한 순서에 의해서만 선언되고 사용된다. Positional, Arbitrary, Keyword 순서를 가지며, 절대적이다. 함수가 인자를 받아서 이 순서를 토대로 인자를 배정함.
1 Positional Arguments
위치 인자이다. 넘어온 데이터나 매개변수의 위치의 순서에따라 인자를 배정하며 가장 높은 우선순위를 준다. 함수를 사용할 때 최소한 positional argument가 선언된 갯수 만큼의 인자를 전달해야한다. 이는 다른 두 인자 타입과 다르게 필수적으로 값의 존재를 요구한다. 함수 정의에서 선언된 positional arguments의 갯수와 동일한 갯수의 인자는 필수적으로 전달해주어야하며, 이를 어기면 파이썬에서는 인자에 값을 배정하지못해 에러를 발생시킨다.
2 Arbitrary Arguments
실제로 사용하는 경우는 적다. 가변 갯수 인자라고도 부르며, 앞에 별(*)을 붙혀 Arbitrary 라는 것을 선언한다. 이 형태의 인자는 0개 이상의 값을 전달받아 하나의 튜플로 묶어서 함수 내에서 사용함.(ex:애스터리스크) 몇개를 받아도 하나로 묶어서 함수안에서 자유롭게 사용이 가능하다. 가변적이게 상황에따라 갯수를 달리해 함수에 전달하게 되는 경우 매유 유용하다. 우선순위는 positional argument 보다 낮으며, positional arguments 를 모두 배정하고 남은 변수들이 이자리에 배정된다. 남는 값이 없다면 빈 튜플이 된다.
3 Keyword Arguments
이방식은 크게 둘로 나눈다. 하나는 positional argument와 같은 방식으로 선언하며 기본값을(default 매개변수)주는 형식이고, 하나는 key-value map을 전달받아 사용하는 방식이다.
key value-maping 인자 이름과 인자에 할당할 값을 특정하는 것이다. key-value 매핑이된 인자들을 가변갯수로 받으려면 def func(**kwargs):
와 같이 **
를 쓰면 된다. dict 형식으로 매핑이 전달된다.
위의 3가지 형식의 인자는 하나의 함수 정의시에 섞어서 사용이 가능하다. 이는 위와 같이 인자의 우선순위가 있기 때문이다. positional-arbitrary-keyword 형태가 되어야한다. keyword는 맨뒤로 몰아놓아야 이름없는 변수들을 모두 배정할 수 있을것이며 필수적인 positional은 인자들이 앞에 작성되어야 전달받은 값을 꼭 필요한 곳부터 배정할수 있기 때문일것 같다.
우선순위는 다음의 링크를 참고하자.
https://getkt.com/blog/python-keyword-only-arguments/
def func (num1=10,num2=20,num3=30):
print(num1,num2,num3)
위의 함수에서 만약 c와 b에만 다른 값을 넣어주고 싶을때는 어떻게? 키워드인자를 지정하면 된다.
func(num3=50,num2=99)를 하면 num3에 50이, num2엔 99가 들어가게 된다.
키워드 인자값을 넘겨줄 때에는 인자 순서와 상관없이 나열 할 수 있다.
def func (num1,num2,num3=30):
print(num1,num2,num3)
위의 코드에서 func(10,20)을 선언할 경우, num1=10, num2=20, num3은 default 매개변수가 작동되어 30이 들어가게되고, func(10,20,50)을 할 경우 default 매개변수가 작동되지않아 num3엔 50이 들어가게 된다. 함수를 호출할 때 주는 순서대로 매개변수에 값이 할당된다는 것을 알 수 있다.
문제는 최초의 호출 시에만 지정된 값으로 초기화되고 이후의 호출에서는 그렇지 않다. 리스트나 딕셔너리 같은 객체를 default 매개변수로 사용할때에 문제가 생길 수 있다.
def func(num, list=[]):
list.append(num)
print(list)
func(1)을 하면 리스트에 1이 추가되고, func(2)를하면 리스트가 1,2가 들어간다. 축적되는것이다.
* 위의 리스트 축적 문제 해결방법
def func(num, list=None):
if list is None:
list = []
list.append(num)
pritn(list)
- 파이썬의 전역변수
형식 ) 인자값과 매개변수를 주지말고 , 함수 내부에 global 전역변수명 을 선언한다
ex ) 함수내부에 global 전역변수명
* 전역변수 예제
a = 1
def func ():
global a
a += 10
return a
func()
print(a)
- 파이썬의 lambda 람다함수
def 키워드를 사용할 수 없거나 함수를 정의하기 귀찮을때 사용한다.
매개변수와 함수정의(수식)의 구분을 : (콜론)으로 해준다 , 호출하는방식은 일반함수 호출과 같다.
형식 ) 람다함수명 = lambda 매개변수:함수정의
ex ) 람다함수 = lambda 매개변수1,매개변수2:매개변수1+매개변수2
# lambda 함수 에제
lam = lambda a,b:a+b
print(lam(10,20))
lambda 람다 함수에는 def함수정의와 다르게 리스트를 사용할 수 있다
lambda 함수를 리스트로 만들어 각각의 인덱스에 함수를 넣을 수 있다
* lambda 리스트함수 예제
lam = [lambda a,b:a+b , lambda a,b:a*b]
print(lam[0](10,20))
print(lam[1](10,20))
* 함수정의시 매개변수의 *(애스터리스크) 사용법
>> 형식 ) def 함수이름 (*매개변수):
>> 함수정의시 매개변수에 *(애스터리스크)가 붙으면 여러개의 값을 받아서 튜플형태로 저장한다는뜻
>> 예제 ) def Method (*numbers):
인자값이 두개이상인 경우 애스터리스크와 매개변수 같이 사용하게 되는데, 애스터리스크가 항상 뒤에있어야한다
>> ex ) def 함수 s_sum (일반매개변수,*애스터리스크매개변수)
>> 이유는 애스터리스크매개변수가 일반매개변수보다 앞에 있을시 모든 인자값이 애스터리스크가 받게된다
* 애스터리스크 예제
def s_sum (*nums):
sum = 0
for cnt in nums:
sum += cnt
return sum
t = [0,0,0,0,0]
for cnt in range(5):
t[cnt] = int(input('{}번째 수 입력: '.format(cnt+1)))
sn = s_sum(t[0],t[1],t[2],t[3],t[4])
print(sn)
**(애스터리스크 두개) 애스터리스크 두개가 붙으면 여러자료의 인자값을 받아 사전형 매개변수로 받는다
>> 형식 ) def 함수명 (**애스터리스크매개변수명)
>> 인자값 작성시 key명을 문자로 줄시에 ''(홑따옴표)를 안붙혀도 된다
>> 인자값 작성시 key 와 value의 구분을 :(콜론)이 아닌 =(이퀄스사인)으로 작성한다
>> ex ) s_sum함수호출(key1=10,key2=20)
**(애스터리스크 두개) 예제
def dict_sum (**args):
sum = 0
for cnt in args:
sum += args[cnt]
return sum
print(dict_sum(자바=10,c언어=20))
*(애스터리스크 한개) 와 **(애스터리스트 두개) 가 동시에 사용할 수 있다
>> 동시사용시에는 반드시 * 를 인자값으로 먼저주고 ** 를 맨마지막 인자값으로 준다
>> * 과 ** 가 동시사용되면 키와값이 있는 인자값은 자동으로 ** 로 넘겨진다
* 와 ** 동시사용 예제
def func (*tupargs,**dicargs):
for cnt in tupargs:
print(cnt)
for cnt in dicargs:
print(cnt,dicargs[cnt])
return 0
func('1','2','3',dic1=1,dic2=2)
먼저 class 클래스명: 을 작성 후 , def init (self,매개변수): 로 생성자를 작성한다.
클래스생성이나 클래스내부 함수호출시 , 인자값을 적지않아도 무조건 디폴트매개변수로 첫번째에 self 라는 매개객체로 자동으로 자기자신의 객체를 매개객체로 준다.
* 클래스생성, 클래스생성자 예제
class Student:
def __init__(self, name, age):
self.name = name self.age = age
def aboutMe(self):
print("제 이름은 " + self.name + "이며, 제 나이는 " + str(self.age) + "살입니다.")
>>> objectStudent = Student("김철수", 18)
>>> objectStudent.aboutMe() 제 이름은 김철수이며, 제 나이는 18살입니다.
객체가 생성될 때 호출되는 생성자가 있다면, 반대로 객체가 소멸 할 때 호출되는 소멸자가 있다.
파이썬에서는 del라는 이름으로 이미 정의가 되어있다.
class 클래스명:
def __del__(self):
문장
* 소멸자 예제
class IceCream:
def __init__(self, name, price):
self.name = name
self.price = price print(self.name + "의 가격은 " + str(price) + "원 입니다.")
def __del__(self):
print(self.name + " 객체가 소멸합니다.")
>>> objectIc = IceCream("월드콘", 1000) 월드콘의 가격은 1000원 입니다.
>>> del objectIc