파이썬의 함수는 수학의 함수와 동일하다.
파이썬에서 기본으로 제공하는 내장함수와 사용자가 직접 선언하는 사용자 함수가 있다.
함수는 특정 기능을 재사용하기 위해서 사용한다.
함수는 def 키워드, 함수명, :, 들여쓰기를 이용해서 선언
함수명과 '()'를 이용해서 함수를 호출
def addCal():
n1 = int(input('n1 입력 : '))
n2 = int(input('n2 입력 : '))
print(f'n1+n2 = {n1+n2}'))
addCal()
함수 호출 시 함수에 데이터를 전달할 수 있다.
인수와 매개변수 개수는 일치해야 한다.
매개변수 개수가 정해지지 않은 경우 ''를 이용한다. (ex. numbers)
def addFun(n1, n2): # n1,n2 매개변수 2개
print(f'{n1} + {n2} = {n1+n2}')
addFun(10,20) # 10,20 인수 2개
return 키워드를 이용하면 함수 실행 결과를 호출부로 반환할 수 있다.
함수가 return을 만나면 실행을 종료한다.
def calculator(n1, n2):
result = n1+n2
return result #함수 호출부로 실행 결과 반환
returnValue = calculator(20,10)
print(f'returnValue: {returnValue}')
returnValue: 30
전역변수 : 함수 밖에서 선언된 변수로 어디에서나 사용은 가능하지만 함수 안에서 수정할 수는 없다.
num_out = 10
def printNumbers():
print(f'num_out: {num_out}')
printNumbers()
print(f'num_out: {num_out}')
num_out: 10
num_out: 10
num_out = 10
def printNumbers():
num_out = 20
print(f'num_out: {num_out}')
printNumbers()
print(f'num_out: {num_out}')
num_out: 20
num_out: 10
지역변수 : 함수 안에 선언된 변수로 함수 안에서만 사용 가능하다.
def printNumbers():
num_in = 20
print(f'num_in: {num_in}')
printNumbers()
num_in: 20
def printNumbers():
num_in = 20
print(f'num_in: {num_in}')
print(f'num_in: {num_in}')
NameError: name'num_in' is not defined
global 키워드 : global을 사용하면 함수 안에서도 전역변수의 값을 수정할 수 있다.
num_out = 10
def printNumbers():
global num_out
num_out = 20
print(f'num_out: {num_out}')
printNumbers()
print(f'num_out: {num_out}')
num_out: 20
num_out: 20
중첩함수 : 함수안에 또 다른 함수가 있는 형태이다.
내부 함수를 함수 밖에서 호출할 수 없다.
lambda함수 : lambda 키워드를 이용하면 함수 선언을 보다 간단하게 할 수 있다.
def calculator(n1, n2):
return n1+n2
returnValue = calculator(10,20)
print(f'returnValue: {returnValue}')
-------------------------------------
calculator = lambda n1, n2: n1+n2
returnValue = calculator(10,20)
print(f'returnValue: {returnValue}')
모듈 : 이미 만들어진 훌륭한 기능으로 사용자는 쉽게 사용할 수 있다.

파이썬 모듈은 내부 모듈, 외부 모듈 그리고 사용자 모듈로 구분할 수 있다.
모듈은 특정 기능을 가지고 있는 파이썬 파일을 말한다.
# calculator.py
def add(n1,n2):
print(f'덧셈 결과: {n1+n2}')
def sub(n1,n2):
print(f'뺄셈 결과: {n1-n2}')
def mul(n1,n2):
print(f'곱셈 결과: {n1*n2}')
def div(n1,n2):
print(f'나눗셈 결과: {round(n1/n2, 2)}')
#module.py
import calculator #모듈 사용
calculator.add(20,10)
calculator.sub(20,10)
calculator.mul(20,10)
calculator.div(20,10)
import 키워드를 이용해서 모듈을 임포트한다.
as 키워드를 입력해서 모듈 이름을 단축 시킬 수 있다.
(ex. import calculator as cal)
from ~ as 키워드를 이용해서 모듈의 특정 기능만 사용할 수 있다.
(ex. from calculator import add)
패키지를 이용하면 관련 있는 모듈을 그룹으로 관리할 수 있다.

site_packages : site-packages에 있는 모듈은 어디서나 사용할 수 있다.
객체지향 프로그래밍 : 객체를 이용한 프로그램으로 객체는 속성과 기능으로 구성된다.
객체 ( object ) = 속성 ( attribute) + 기능 ( function )
객체는 클래스에서 생성된다.
객체 사용의 장점 : 코드 재사용, 모듈화에 좋다.
클래스는 class 키워드와 속성(변수) 그리고 기능(함수)를 이용해서 만든다.
class Car: # 클래스 선언
def __init__(self, color, length):
self.color = color
self.length = length # 생성자, 속성
def doStop(self):
print('STOP!!') # 기능
def doStart(self):
print('START!!') # 기능
car1 = Car('red', 200)
car2 = Car('blue', 300) # 객체 2개 생성
얕은 복사 : 객체 주소를 복사하는 것으로 객체 자체가 복사되지 않는다.
깊은 복사 : 객체 자체를 복사하는 것으로 또 하나의 객체가 만들어진다.
# 선수의 원본 점수를 이용해서 평균을 출력하고, 최고값과 최저값을 제외한 평균을 출력하는 프로그램을 만들어보자
plaOriSco = [8.7, 9.1, 8.9, 9.0, 7.9, 9.5, 8.8, 8.3]
plaCopSco = plaOriSco.copy()
plaOriSco.sort()
plaCopSco.sort()
plaCopSco.pop(0)
plaCopSco.pop()
print(f'plaOriSco: {plaOriSco}')
print(f'plaCopSco: {plaCopSCo}')
oriTot = round(sum(plaOriSco), 2)
oriAvg = round(oriTot / len(plaOriSco), 2)
print(f'Original Total: {oriTot}')
print(f'Original Average: {oriAvg}')
copTot = round(sum(plaCopSco), 2)
copAvg = round(oriTot / len(plaCopSco), 2)
print(f'Copy Total: {copTot}')
print(f'Copy Average: {copAvg}')
print(f'oriAvg - copAvg: {oriAvg - copAvg}')
상속 : 클래스는 또 다른 클래스를 상속해서 내 것처럼 사용할 수 있다.
# 덧셈, 뺄셈 기능이 있는 클래스를 만들고, 이를 상속하는 클래스를 만들어서 곱셈과 나눗셈 기능을 추가해 보자.
class CalculatorSuper:
def add(self, n1, n2):
return n1+n2
def sub(self, n1, n2):
return n1-n2
--------------------------
class CalculatorChild(CalculatorSuper):
def mul(self, n1, n2):
return n1*n2
def div(self, n1, n2):
return n1/n2
---------------------------
cal = CalculatorChild()
print(f'cal.add(10,20): {cal.add(10,20)}')
print(f'cal.sub(10,20): {cal.sub(10,20)}')
print(f'cal.mul(10,20): {cal.mul(10,20)}')
print(f'cal.div(10,20): {cal.div(10,20)}')
다중상속 : 2개 이상의 클래스를 상속한다.
객체가 생성될 때 생성자를 호출하면 __init__()가 자동 호출된다.

__init__()가 속성을 초기화 한다.
상위 클래스의 속성을 초기화하기 위해서 super()를 이용한다.

# 중간고사 클래스와 기말고사 클래스를 상속관계로 만들고 각각의 점수를 초기화하자. 또한 총점 및 평균을 반환하는 기능도 만들어보자
class MidExam:
def __init__(self, s1, s2, s3):
print('[MidExam] __init__()')
self.mid_kor_score = s1
self.mid_eng_score = s2
self.mid_mat_score = s3
def printScores(self):
print(f'mid_kor_score: {self.mid_kor_score}')
print(f'mid_eng_score: {self.mid_eng_score}')
print(f'mid_mat_score: {self.mid_mat_score}')
class EndExam(MidExam):
def __init__(self, s1,s2,s3,s4,s5,s6):
print('[EndExam] __init__()')
super().__init__(s1, s2, s3)
self.end_kor_score = s4
self.end_end_score = s5
self.end_mat_score = s6
def printScores(self):
super().printScores()
print(f'end_kor_score: {self.mid_kor_score}')
print(f'end_eng_score: {self.mid_eng_score}')
print(f'end_mat_score: {self.mid_mat_score}')
def getTotalScore(self):
total = self.mid_kor_score + self.mid_eng_score + self.mid_mat_score
total += self.end_kor_score + self.end_eng_score + self.end_mat_score
return total
def getAverageScore(self):
return self.getTotalScore() / 6
exam = EndExam(85, 90, 88, 75, 85, 95)
exam.printScores()
print(f'Total: {exam.getTotalScore()}')
print(f'Average: {round(exam.getAverageScore(), 2)}')
하위 클래스에서 상위 클래스의 메서드를 재정의한다.

상위 클래스에서 하위 클래스에 메서드 구현을 강요한다.

예외 : 문법적인 문제는 없으나 실행 중 발생하는 예상하지 못한 문제이다.
n1 = 10; n2 = 0
print(n1/n2)
print(n1*n2)
print(n1-n2)
print(n1+n2)
---------------
ZeroDivisionError: division by zero
예외 종류 :
예외 관련 클래스는 Exception 클래스를 상속한다.

예상하지 못한 예외가 프로그램 전체에 영향이 없도록 처리함
예외 발생 예상 구문을 try~except로 감싼다.
n1 = 10; n2 = 0
try:
print(n1/n2)
except:
print('예상치 못한 예외가 발생했습니다.')
print('다른 프로그램 실행에는 문제 없습니다.')
print(n1*n2)
print(n1-n2)
print(n1+n2)
-----------------------------------------
예상치 못한 예외가 발생했습니다.
다른 프로그램 실행에는 문제 없습니다.
0
10
10
nums = []
n =1
while n < 6:
try:
num = int(input('input number: '))
except:
print('예외 발생')
continue
else: # 예외가 발생하지 않으면 실행
if num % 2 ==0:
nums.append(num)
n +=1
else:
print('입력한 숫자는 홀수 입니다.', end=' ')
print('다시 입력 하세요.')
continue
try:
inputData = input('input number: ')
numInt = int(inputData)
except:
print('exception raise!!')
print('not number!!')
numInt = 0
else:
if numInt % 2 == 0:
print('inputData is even number!!')
else:
print('inputData is odd number!!')
finally:
print(f'inputData: {inputData}') #항상 실행
-----------------------------------------------------
input number: 10
inputData is even number!!
inputData: 10
input number: 가나다
exception raise!!
not number!!
inputData: 가나다
Exception 클래스는 예외 담당 클래스이다.
raise 키워드를 이용하면 예외를 발생시킬 수 있다.
# 사용자가 문자 메시지를 보낼때 10글자 이하면 SMS로 발송하고, 10글자를 초과하면 MMS로 발송하는 프로그램을 예외처리를 이용해서 만들어보자.
def sendSMS(msg):
if len(msg) > 10:
raise Exception('길이 초과!! MMS전환 후 발송!!, 1)
else:
print('SMS 발송!!)
def sendMMS(msg):
if len(msg) <= 10:
raise Exception('길이 미달!! SMS전환 후 발송!!', 2)
else:
print('MMS 발송!!)
msg = input('input message: ')
try:
sendSMS(msg)
except Exception as e:
print(f'e: {e.args[0]}')
print(f'e: {e.args[1]}')
if e.args[1] == 1:
sendMMS(msg)
elif e.args[1] == 2:
sendSMS(msg)
Exception 클래스를 상속해서 사용자 예외 클래스를 만들 수 있다.
class NotUseZeroException(Exceptioon):
def __init__(self, n):
super().__init__(f'{n}은 사용할 수 없습니다!!')
def divCalculator(num1, num2):
if num2 == 0
raise NotUseZeroException(num2)
else:
print(f'{num1} / {num2} = {num1/num2}')
num1 = int(input('input number1: ')
num2 = int(input('input number2: ')
try:
divCalculator(num1, num2)
exception NotUseZeroException as e:
print(e)
-----------------------------------------
input number1: 10
input number2: 0
0은 사용할 수 없습니다!!
open(), read(), write(), close()를 이용한 텍스트 파일 다루기
write() : 파일에 문자열 쓰기
read() : 파일 문자열 읽기
파일 모드는 파일을 어떤 목적으로 open 할지 정한다.
파일 닫기(close)를 생략할 수 있다.
writelines()는 리스트(List) 또는 튜플 데이터를 파일에 쓰기 위한 함수이다.
readlines() : 파일의 모든 데이터를 읽어서 리스트 형태로 반환
readline() : 한 행을 읽어서 문자열로 반환