Ch.4 Functions
앞서 설명했던 프로그래밍의 네가지 패턴 중 우리가 유일하게 한가지 짚지 않고 넘어갔던 부분이 있었다.
그 부분이 오늘 설명할 부분인데, 바로
"Store & Reuse" 부분이다.
Function 함수는 코드를 저장했다가 재사용하는 것이다.
프로그래밍에서 중요한 한가지는 같은 작업을 반복해서 하고 싶지 않다는 것이다.

상상해보자.
만약에 다섯줄짜리 코드가 있고
이 코드를 프로그램에서 다른 열 두 군데 정도에 존재한다면, 그 열두 군데 모두를 찾아서 고쳐야 할 것이다. 그래서 이 코드들을 한 곳에 모아두고 호출해서 재사용하는 것이 경제적일 수 있다.
이것이 저장과 재사용 store & reuse 아이디어라고 할 수 있다. 이것은 파이썬에서 함수가 작동하는 방식이다.
"def" 는 if 구문과 비슷한데 뒤에 콜론으로 끝이 난다.
또, 들여쓰기 된 코드 블록이 있고, 또 들여쓰기된 블록을 다시 내어쓰면 함수가 끝이 난다.
그래서 함수는 두 개의 구문으로 이루어진다.
여기서 꼭 이해하고 넘어가야 하는 부분은 def 부분이 실제로 바로 실행되는 코드는 아니라는 점이다.
이 부분은 사실 코드를 기억하는 부분 Store하는 부분이다. 이 def 구문으로 "파이썬을 확장시켰다!" 고도 이해해볼 수 있다.(예약어로 한정되어 있는 파이썬에서?)

사실 우리는 이미 처음부터 함수를 사용하고 있었다.
print()도 함수라는 것을 우리는 알고 있었다.
우리가 print 키워드를 볼 때 마다, print()와 괄호 사이에 무언가 있으면 print 함수를 호출하고 있었다. 이것이 문법이다. 두개의 소괄호와 함께 있는 키워드가 함수를 부를 때, 사용하는 문법이다.
이런 print, input, type 등등의 함수들은 모두 파이썬의 시작과 함께 있던, 파이썬을 설치하던 때 부터 정의되어 있던 내장함수다.
그리고 우리가 직접 정의하고 사용하는 또 다른 함수가 있고 이러한 함수들을 위해 def가 필요한 것이다.
우리는 새로운 예약어를 만들어 파이썬 언어를 확장할 수 있다!
이렇게 만든 함수는 함수이름, 괄호, 인자를 이용해 함수를 호출할 수 있다.

함수의 호출은 코드 'x+1'과 크게 다르지 않은
계산해야할 우변의 무언가이다.
함수 코드를 실행하고 이 전달인자를 전달하여
결과로 남은 값을 반환값이라 부른다.
예를 들어, 위 그림처럼
'Hello world' 라는 문자열을 인자로 전달 받으면,
사전 편집 순서상 가장 마지막에 나올 문자를 찾을 것이다. 여기서는 명백하게 w가 가장 뒤에 순서이기 때문에,
값이 크므로 w를 돌려받는다.
결과로 남은 이 값을 반환값이라 한다.
언젠가 옛날에 파이썬이 처음 만들어질 때,
누군가가 코드를 적어서 무언가를 집어 넣고
모든 문자를 읽는 작은 반복문과 문자열인지 리스트인지
알아내는 코드를 집어넣고 기타 등등을 집어 넣어 놓은 것일 것이다.
Max 함수는 우리가 직접 저장하지 않았지만,
이미 내장되어 있기 때문에 재사용이 될 수 있다.
이처럼, 미리 만들어져 있기 때문에 따로 정의 하지 않고
바로 호출할 수 있도록 만들어 놓은 것이다.


def 키워드부터 싲가해 곧 보게될 임의의 인자를 가지고 있다. 인자가 있기 때문에 괄호가 사용된다.
함수의 이름은 몇가지 규칙을 갖는데,
이는 변수 이름 규칙과 같다.
함수의 본문은 들여쓰기를 하는데, 이때 내가 원하는 것들을 넣어 작성하면 된다. 코드 블럭을 내어쓰기를 하면 마침내 필요한 것들의 정의가 끝난다.
여기서 중요한 것은 이 코드들이 바로 실행되는 것이 아니라, 단순히 이제 기억을 했다는 것이다. 저장하는 것이다.


greet라는 이름을 가진 함수에서
lang이 바로 인자이다.
이 인자는 함수 안으로 전달이 된다.
이 lang이라는 변수는 함수가 실행되는 동안에만 존재.
실제 변수와 완전히 같은 의미는 아니지만,
여기에 있는 첫번째 매개변수를 어떻게 사용할 수 있을지
참조할 수 있게 하는 임시의 변수같은 느낌이다.
따라서, lnag은 우리의 첫번째 매개변수이다.
우리는 매개변수를 받을 것이고,
lang이 매개변수로 받은 것이 무엇인지
알려줄 임시의 변수라는 점이다.
지금까지는 함수에 무엇을 집어 넣었다면,
무언가 다시 가져오는 것을 우리는 '반환'이라고 한다.
반환문은 두가지 일을 가능하게 한다.
첫번째로 종료이다.
다음 줄로 넘어가지 않고 반환하고 끝낸다.
두번째로 함수 결과를 잔여값으로
무엇이 남기길 원하는지 지정할 수 있다.
값을 반환하는 함수를 fruitful하다고 표현하기도 한다.

앞서서, 첫번째 매개변수로 언어를 받고 출력문을 실행하는 대신에 출력할 값을 반환하도록 수정해서 만든 코드이다.
(함수가 직접 출력하도록 하면 코드가 볼품없어진다고 한다.)

함수를 정의할 때 하나 이상의 매개변수를 설정할 수 있다. 이런 경우에, 매개변수 설정한 만큼 인자로 전달하지 않으면 traceback error가 발생할 수 있다.
나중에는 매개변수를 선택적으로 설정할 수 도 있다.

반환값을 가질 필요가 없다는 것은
값과 함께 반환을 호출하지 않는다는 뜻인데,
반환은 항상 함수의 마지막 줄에서 일어난다.
이것이 함수가 작동하는 기본방식이다.
혹자는 꼭 함수를 써야한다고 말하기도 한다.
함수에서 중요한 것은 저장하고 호출하는 것을 이해한 함수의 개념이다. 이것이 핵심이다.
단 몇줄의 코드를 작성하기 위해 반드시 함수를 사용해야 한다는 것은 무의미하다고 할 수 있다..
함수를 적게 사용하는 것에 대해 너무 걱정하지 말자.
다만, 반복해서 코드를 작성하는 것에 지치는 때가 온다면 그때 함수의 개념을 알고 비로소, 함수를 사용해보아도 좋다.