함수는 이미 수학에서 배운 개념입니다.
본 수업에서는 Python을 통해서 수학의 함수와 동일한 수학 계산을 하는 경우, 그리고 보다 폭넓은 기능을 제공하는 함수를 만나게 됩니다.
이러한 과정에서 Python이 이미 제공하는 수많은 함수들을 익히고, 사용자가 스스로 함수를 만드는 과정을 경험하게 됩니다.
지금까지 배워온 수학과목들을 통해서 우리는 함수라는 개념을 익히 알고 있습니다.
예를 들어 다음과 같이 입력 값 x
를 받아서, 함수의 결과 값을 출력값 y
에 대입하는 수학 함수인 f(x)
의 개념을 알고 있습니다.
$y=f(x)$
주어진 수학 공식에서 함수 f(x)
는 정해진 약속을 수행하는 것도 알고 있습니다.
즉 f(x) = x + 1
일때, 만약 x
가 1의 값을 가진다면, 우리는 앞서의 $y=f(x)$를 통해서 y
에 2의 값이 대입됨을 알고 있습니다.
Python과 같은 프로그래밍 언어도 수학과 마찬가지로 함수가 있습니다.
프로그래밍 언어의 함수는 수학의 함수처럼 숫자의 계산을 포함하면서, 보다 다양한 기능을 제공한다는 점에서 차이가 있습니다.
프로그래밍 언어의 함수를 사용하면 파일을 만들고 업데이트 하거나, 화면에 그림을 그리거나, 스피커로 소리를 만드는 등 다양한 작업이 가능합니다.
하지만 수학의 함수와 동일하게 매우 간단한 원칙을 가지고 있는데, 이는 "입력을 받아, 정해진 작업을 수행하고, 필요시 정해진 결과를 돌려준다"는 것입니다.
앞으로 여러분은 Python에서 이미 만들어서 제공하는 함수들과 여러분이 직접 만들어서 사용하는 함수들을 만나게 됩니다.
Python과 같은 프로그래밍 언어는, 이미 다양한 기능을 수행하는 함수들을 내장하고 있으며, 예를 들면 다음과 같습니다.
abs(x)
: 입력 받은 정수 혹은 실수 변수인 x
의 절대값을 계산합니다.
pow(x, y)
: 입력 받은 x
의 y
거듭제곱을 계산합니다.
round(x)
: 입력 받은 x
를 소수점 다음에 대해서 반올림한 값을 계산합니다.
다음의 코드를 아래 입력창에 한번에 입력하여, 실행함으로서 확인이 가능합니다.
print(abs(-9))
print(pow(3,2))
print(round(4.3))
print(abs(-9))
print(pow(3,2))
print(round(4.3))
9 9 4
Python은 매우 많은 내장 함수를 기본적으로 제공하므로, 이에 대해서는 다음의 웹사이트를 방문하여 천천히 살펴보도록 합니다.
Python 3.x의 내장함수 설명 웹사이트: https://docs.python.org/ko/3/library/functions.html#round
혹은 Python 문법의 사용법을 모를때 호출하면 유용하게 사용할 수 있는, 함수 help()
를 사용하는 것도 좋은 방법입니다.
즉 본인이 궁금한 함수의 이름을 help()
함수의 입력 파라메타로 입력하면, 이에 대한 짧은 설명을 Python이 알려줍니다.
시험 삼아, abs() 함수에 대한 사항을 알아보기 위하여, 다음의 입력창에 help(abs)
를 입력후 실행해 보십시오.
help(abs)
Help on built-in function abs in module builtins: abs(x, /) Return the absolute value of the argument.
Python이 제공하는 내장 함수들 중에는 변수의 타입을 바꿔주는 함수들도 존재합니다.
즉, 앞서의 수업에서 배운 정수/실수 타입에 대해서, 정수를 실수로 혹은 실수를 정수로 바꿔주는 함수들이며, 함수의 이름은 타입명과 동일합니다.
예를 들어 다음의 예제는 각각 실수인 34.6을 정수 34로 바꿔주고,
정수인 21을 21.0의 실수 타입으로 변환하여 주는 것을 알수 있습니다.
다음의 코드를 아래 입력창에 한번에 입력하여, 실행함으로서 확인이 가능합니다.
print(int(34.6))
print(float(21))
print(int(34.6))
print(float(21))
34 21.0
Python 언어가 기본적으로 제공하는 내장 함수외에, 컴퓨터 프로그래머가 필요한 함수를 직접 만드는 것이 가능합니다.
화씨 온도인 F를 섭씨 온도인 C로 변환하는 다음의 수학 공식을 Python을 사용한 사용자 정의 함수로 만들어 보겠습니다.
Fahrenheit to Celsius (수학)
: $C=(F-32)*\frac{5}{9}$
사용자 정의 함수를 만들기 전에 다음의 사항을 미리 고민해야 합니다.
(1) 함수의 이름은 무엇인가?
(2) 함수의 입력 파라메타는 무엇인가? (갯수, 종류 등)
(3) 함수의 기능은 무엇인가? (입력 파라메타를 받아서 어떤 작업을 해야하는가 등)
(4) 함수의 출력 파라메타는 무엇인가? ((3)의 작업을 마친후, 함수를 호출한 곳으로 어떤 결과를 돌려줘야 하는가 등)
각각에 대해서 미리 답을 해봅시다.
(1) 함수의 이름: convert_to_celsius
(2) 함수의 입력 파라메타: 화씨로 변환할 섭씨 온도 숫자 하나
(3) 함수의 기능: 화씨를 섭씨로 바꾸는 공식에 맞춰서, 입력 파라메타에서 32를 뺀후 $\frac{5}{9}$를 곱함
(4) 함수의 출력 파라메타: 화씨로 변환한 온도 숫자 하나
이제 정의한 함수를 Python 언어로 작성하면 다음과 같습니다.
def convert_to_celsius(fahrenheit):
return (fahrenheit - 32) * 5/9
[1번줄 설명]
Python에서 사용자 정의 함수를 새롭게 만들때에는 def
문법으로 시작합니다.
def
문법을 사용하여 새롭게 convert_to_celsius()
함수를 정의하는 것으로 시작했으며,
미리 정의한 것처럼, 입력 파라메타를 하나 받는데, 입력 파라메타의 이름을 프로그램 목적에 맞게 fahrenheit
라고 명명했습니다.
이렇게 입력 파라메타도 변수이므로, 앞서 변수에 대한 수업에서 배운 것처럼, 의미가 명확하게 이름을 지어줍니다.
마지막으로 새롭게 정의하는 함수에 대한 것임을 Python에 알려주기 위하여 :
으로 마칩니다.
[2번줄 설명]
이제 convert_to_celsius()
함수의 실제 내용을 작성하는 것을 시작하는 줄입니다.
Python에서는 사용자 정의 함수를 정의하는 1번줄 다음의, 2번줄 부터는 공백으로 시작을 해야 합니다.
예제의 경우는 4칸의 공백을 주었고, 일반적으로 2칸 혹은 tab을 사용합니다.
만약에 Python 언어를 인식하는 개발도구 혹은 에디터를 사용한다면, 이런 경우를 자동으로 인식하여 자동으로 공백을 삽입하니 편리합니다.
Jupyter Notebook도 자동으로 함수의 시작을 인식하고 공백을 삽입하는 것을 볼수 있습니다.
실제 온도 변환을 수행할 (3)의 함수 기능을 작성한 것을 볼 수 있습니다.
return
문법은 convert_to_celsius(212)
처럼 함수에 입력값을 주면서 호출한 곳으로 결과 값을 전달하는 기능을 합니다.
따라서 2번줄은 fahrenheit
변수에서 (3)의 기능에 따라, 32를 빼고 $\frac{5}{9}$를 곱한 결과를 함수 호출한 곳에 돌려줍니다.
아래의 입력창에, 위에서 정의한 convert_to_celsius()
함수를 입력하고 실행해 봅니다.
아무런 결과가 나타나지 않았다면, 에러(error)가 없는 것입니다.
Python이 에러를 나타낸다면, 위의 프로그램 코드를 잘보고 오타 없이 타이핑해서 에러를 없애 봅니다.
def convert_to_celsius(fahrenheit):
return (fahrenheit - 32) * 5/9
에러가 나지 않았다면, 이제 Python은 여러분이 만든 convert_to_celsius()
함수를 기억하고 있습니다.
이제 만든 함수를 사용(호출)해 볼까요?
아래의 입력창에 다음과 같이 화씨 212도를 섭씨로 변환하는 함수 호출을 실습해 보십시오.
convert_to_celsius(212)
convert_to_celsius(212)
100.0
def convert_to_celsius(fahrenheit):
return print((fahrenheit - 32) * 5/9)
print(convert_to_celsius(212))
100.0 None
위와같이 python 초심자들은 return에 print를 많이 사용하는데 위와같은 사용은 일반적으로 지양합니다. print함수는 우리가 직접적으로 값을 볼때 사용하는 함수이므로 위와같이 print(convert_to_celsius(212))처럼 사용하게되면 print한 결과를 또 프린트하게 되므로 None 이라는 결과가 출력되고 print(print(100.0)) 과 같은 결과를 출력하게 됩니다.
def convert_to_celsius(fahrenheit):
return (fahrenheit - 32) * 5/9
print(convert_to_celsius(212))
100.0
지난 시간의 변수 이름 정하기와 이번 시간의 함수 이름을 정하는 단계에서 반드시 염두에 두어야 하는 것은 "예약어(reserved words)"입니다.
Python 언어의 예약어는 문법으로 사용하는 단어들이기에 변수나 함수의 이름으로 사용하면 안됩니다.
주요 예약어는 다음과 같습니다.
and, del, from, not, while, as, elif, global, or, with, assert, else, if,
break, except, import, print, class, exec, in, raise, continue, finally,
pass, yield, def, for, lambda, try, is, return
우리는 앞서의 수업에서 필요한 시점에 필요한 값을 저장하는 변수를 배웠고, 위의 예제들에서도 사용하였습니다.
이미 만들어진 변수에 대해서, 이 변수가 만들어진 지점이 어디냐에 따라서, 이후 사용 가능하거나 불가능한 경우가 발생합니다.
대표적인 사례는 지역변수(Local Variables) 입니다.
지역변수를 이해하기 위하여, 앞서 만든 사용자 정의 함수를 다시 봅니다.
def convert_to_celsius(fahrenheit):
return (fahrenheit - 32) * 5/9
사용자 정의 함수 convert_to_celsius()
안에는 변수 fahrenheit
가 있는 것을 볼수 있습니다.
이는 해당 함수 안에서 만들어서 사용한 변수이며, 따라서 convert_to_celsius()
안에서만 의미가 있는데, 이를 지역변수라고 합니다.
즉, 변수를 사용할 수 있는 지역이 사용자 정의 함수 convert_to_celsius()
안으로 제한되는 것 입니다.
이를 확인해 보기 위하여, 아래의 창에 다음처럼 fahrenheit
변수의 값을 읽어보는 시도를 해봅니다.
print(fahrenheit)
def convert_to_celsius(fahrenheit):
return (fahrenheit - 32) * 5/9
print(fahrenheit)
--------------------------------------------------------------------------- NameError Traceback (most recent call last) <ipython-input-8-21dbca22a964> in <module> 1 def convert_to_celsius(fahrenheit): 2 return (fahrenheit - 32) * 5/9 ----> 3 print(fahrenheit) NameError: name 'fahrenheit' is not defined
시도해본 결과 "name 'fahrenheit' is not defined"
라는 에러가 나는 것을 볼수 있습니다.
즉, 우리가 지금 fahrenheit
변수를 사용한 지점은 convert_to_celsius()
함수 밖이기에,
convert_to_celsius()
함수 안에서만 사용 가능한 fahrenheit
변수를 접근하는 행위는 문제가 있는 것 입니다.
함수를 호출하는 경우는 함수가 필요로 하는 입력 파라메타의 갯수(필요시 입력 파라메타의 타입(들) 및 순서)를 맞춰줘야 합니다.
그리고 함수의 지역 변수는 앞서 convert_to_celsius()
함수의 입력 파라메타 부분 외에 함수의 안에서도 만들어 사용할 수 있습니다.
이를 위해서 간단한 사용자 정의 함수인 quadratic()
을 만들어 봅니다.
def quadratic(a, b, c, x):
first = a * x ** 2
second = b * x
third = c
return first + second + third
아래의 입력창에 위의 quadratic()
를 입력하고 실행하여, 에러가 발생하지 않는 것을 확인 합니다.
def quadratic(a, b, c, x):
first = a * x ** 2
second = b * x
third = c
return first + second + third
quadratic()
함수는 다음과 같은 정의를 통해서 만든 함수입니다.
(1) 함수의 이름: quadratic
(2) 함수의 입력 파라메타: $f(x) = a * x^2 + b * x + c$ 공식에서 a
, b
, c
및 x
값
(3) 함수의 기능: $f(x) = a * x^2 + b * x + c$ 공식을 계산함
(4) 함수의 출력 파라메타: $f(x) = a * x^2 + b * x + c$ 공식의 결과 값을 호출한 곳으로 돌려줌
quadratic()
함수는 총7개의 지역변수를 갖습니다.
4개는 입력 파라메타로 사용하는 a
, b
, c
및 x
이며,
나머지 3개는 함수 내부적인 처리를 위해서 사용하는 first
, second
및 third
입니다.
먼저, 아래의 입력창에 다음의 문장을 통해서 quadratic()
함수를 실행해 봅니다.
print(quadratic(10))
print(quadratic(10))
--------------------------------------------------------------------------- TypeError Traceback (most recent call last) <ipython-input-10-298f6ae8e418> in <module> ----> 1 print(quadratic(10)) TypeError: quadratic() missing 3 required positional arguments: 'b', 'c', and 'x'
다음처럼 입력 파라메타를 제대로 맞춰서 실행해 봅니다.
print(quadratic(2,3,4,2))
print(quadratic(2,3,4,1.0))
print(quadratic(2,3,4,2))
print(quadratic(2,3,4,1.0))
18 9.0
다음처럼 입력 파라메타의 갯수를 4개가 아닌 상태로 주어서 오류를 유발해 봅니다.
print(quadratic(2,3,4))
print(quadratic(2,3,1.0))
print(quadratic(2,3,4))
print(quadratic(2,3,1.0))
--------------------------------------------------------------------------- TypeError Traceback (most recent call last) <ipython-input-12-6a53609292e6> in <module> ----> 1 print(quadratic(2,3,4)) 2 print(quadratic(2,3,1.0)) TypeError: quadratic() missing 1 required positional argument: 'x'
quadratic()
함수의 지역 변수를 함수 바깥에서 접근해서, 오류가 발생하는 것을 확인해 봅니다.
print(first)
print(a)
print(first)
print(a)
--------------------------------------------------------------------------- NameError Traceback (most recent call last) <ipython-input-13-aad687d46c08> in <module> ----> 1 print(first) 2 print(a) NameError: name 'first' is not defined
함수를 호출하는 이유는 함수가 수행한 결과를 받아서 활용하기 위한 목적이 일반적입니다.
이 경우, 함수 호출 결과를 활용 하는 대표적인 방법은 다음과 같습니다.
# Case.1
print(quadratic(2,3,4,1.0))
# Case.2
result = quadratic(2,3,4,1.0)
result = result + 1
print(result)
Case.1의 경우는 함수의 결과를 별도의 변수 없이 print()
문법을 사용하여 화면에 출력만 하는 경우입니다.
Case.2의 경우는 함수의 결과를 새로운 변수(이 경우 result
)에 저장하고, 필요한 추가적인 작업(이경우 결과에 1을 더하고, 화면 출력)을 수행하는 경우입니다.
함수를 만들거나 호출한 용도에 맞춰서, 두가지 방법중 하나를 사용하면 됩니다.
위의 내장 함수 관련 웹사이트를 참조하여, 다음의 각 줄에 해당하는 코드를 작성하고, print()
문법을 사용하여 출력합니다.
(1) -9.2의 절대값
(2) 3^2(3의 2거듭제곱)값
(3) -4.3의 정수값
(4) 21의 실수값
(5) 2와 3중 최소값
(6) 2, -3, 4, 7, -5의 최소값
(7) 2, -3, 4, 7, -5의 최대값
(8) 2, -3, min(4,7), -5 중 최소값
(9) 2, -3, max(4,7), -5 중 최대값
print(abs(-9.2))
print(pow(3,2))
print(int(-4.3))
print(float(21))
print(min(2,3))
print(min(2,-3,4,7,-5))
print(max(2,-3,4,7,-5))
print(min(2,-3,min(4,7),-5))
print(max(2,-3,max(4,7),-5))
9.2 9 -4 21.0 2 -5 7 -5 7
다음의 다섯 함수를 만듭니다.
임시 변수 x, y, z를 만들어서 각각에 적절한 값을 대입한 후,
위에서 정의한 사용자 함수들을 하나 하나 호출하고 난후, 결과값을 print()
문법을 사용하여 출력하도록 합니다.
def sum_(a,b):
return a+b
def multiply(a,b):
return a*b
def subtract(a,b):
return a-b
def multiply_three_numbers(a,b,c):
return a*b*c
def add_and_multiply(a,b,c):
return (a+b)*c
[자가진단] 본인이 만든 LAB 프로그램이 제대로 동작하는지 확인합니다.
아래의 입력창을 수정하지 않고, 그대로 실행해서, 아무런 변화가 없다면 제대로 작성한 것입니다.
만약 에러 화면이 나타난다면, 위에서 정의한 다섯개의 함수(들)를 수정하여 에러가 없도록 다시 작성합니다.
assert sum_(1,2) == 3
assert multiply(1, 2) == 2
assert subtract(1, 2) == -1
assert multiply_three_numbers(1, 2, 3) == 6
assert add_and_multiply(1, 2, 3) == 9
앞서 작성한 add_and_multiply()
함수를, 기본 연산자인 +
와 *
를 사용하지 말고,
sum_()
와 multiply()
함수를 이용하여 동일한 동작을 수행하도록 하며, 이를 new_add_and_multiply()
함수로 정의합니다.
아래의 입력창에 새로운 new_add_and_multiply()
함수를 작성하고, 앞서 정의한 x
, y
, z
를 입력 파라메타로 주어 실행해 봅니다.
def new_add_and_multiply(a,b,c):
return multiply(sum_(a,b),c)
[자가진단] 본인이 만든 LAB 프로그램이 제대로 동작하는지 확인합니다.
아래의 입력창을 수정하지 않고, 그대로 실행해서, 아무런 변화가 없다면 제대로 작성한 것입니다.
만약 에러 화면이 나타난다면, new_add_and_multiply()
함수를 수정하여 에러가 없도록 다시 작성합니다.
assert new_add_and_multiply(1,2,3) == 9
assert new_add_and_multiply(2,3,4) == 20
assert new_add_and_multiply(5,2,-8) == -56
앞서 작성한 quadratic()
함수를, 기본 연산자들을 사용하지 말고,
지금까지 정의한 사용자 정의 함수 및 내장 함수를 '그대로' 이용하여 새롭게 정의하며, 이를 new_quadratic()
함수로 정의합니다.
아래의 입력창에 새로운 new_quadratic()
함수를 작성하고, 적절한 입력 파라메타를 주어 실행해 봅니다.
def new_quadratic(a,b,c,x):
return sum_(sum_(multiply(a,multiply(x,x)),multiply(b,x)),c)
[자가진단] 본인이 만든 LAB 프로그램이 제대로 동작하는지 확인합니다.
아래의 입력창을 수정하지 않고, 그대로 실행해서, 아무런 변화가 없다면 제대로 작성한 것입니다.
만약 에러 화면이 나타난다면, new_quadratic()
함수를 수정하여 에러가 없도록 다시 작성합니다.
assert new_quadratic(2, 3, 4, 2) == 18
assert new_quadratic(4, 7, 1, 9) == 388
assert new_quadratic(-54, 77, 32, 100) == -532268
Step_06_Boolean (0) | 2021.05.18 |
---|---|
Step_05_String (0) | 2021.05.15 |
Step_04_Functions_Part_2 (0) | 2021.05.13 |
Step_02_Variables (0) | 2021.05.07 |
Anaconda3 설치 및 Jupyter notebook 실행 (3) | 2021.05.06 |
댓글 영역