개발하는 일상

처음 시작하는 사람들이 오해하기 쉬운 프로그래밍에서 말하는 함수 본문

개발 기록

처음 시작하는 사람들이 오해하기 쉬운 프로그래밍에서 말하는 함수

롯데빙빙바 2021. 1. 20. 11:24

함수

흔히 함수에 쓰이는 모델


입력과 출력, 블랙박스 등의 개념을 함수를 설명하면서 흔히 사용하지만, 저는 그것이 오히려 약간의 오해를 불러일으킬 수 있다고 생각합니다. 저는 프로그래밍을 처음 접하시는 분들을 자주 만나는데요. 그분들께서 주로 하셨던 잘못된 생각을 소개하며 함수를 알아보겠습니다. 특히, 파이썬의 주피터 노트북 같은 REPL(쉽게 말해서 코드를 실행한 결과를 바로 출력해주는 환경)에서 학습을 시작하셨다면 더욱 이런 오해를 가지기 쉽다고 생각합니다. 함수의 개념이 와 닿지 않았던 분들에게 도움이 되었으면 좋겠습니다.

수학에서의 함수

수학에서 말하는 함수와 프로그래밍에서 말하는 함수는 다르다

우리가 중학교를 거쳐 고등학교까지의 정규과정에서 배웠던 함수에는 반드시 입력(x)과 출력(y)이 존재합니다. y = x 같은 간단한 함수에서부터, 고차함수나 삼각함수 등등 모든 함수는 x가 변할 때 y가 어떻게 변하는지를 수식으로 써놓은 모양입니다. 위에서 봤던 그림은 여기서 말하는 함수를 정말 잘 설명하는 모델입니다.

프로그래밍에서의 함수

함수는 코드를 모아 이름을 붙인 것

제 생각에 프로그래밍에서의 함수는 입력과 출력은 단지 함수의 부산물일 뿐입니다. 함수는 어떤 일을 하는 코드를 모아 이름을 붙인 것입니다. 입력과 출력은 있을 수도, 없을 수도 있습니다. 단지 반복되는 코드를 줄여 하나의 이름으로 불러 쓰기 위해 만든 개념인 것이죠. 코드를 모아서 이름을 붙이다 보니, 어떤 코드에는 입력이 필요할 때도 있고, 출력이 필요할 때도 있습니다. 각각 어떨 때 필요한지, 필요하지 않은지 살펴보겠습니다.

입력(input)

입력은 코드를 실행할 때마다 다른 값이 필요할 때 사용한다

입력이 필요한 함수의 예

아래 코드의 함수 print_avg는 숫자 배열의 평균 값을 터미널에 표시해주는 기능을 하는 함수입니다. 다양한 배열의 평균을 구하기 위해서 만든 함수이므로, 입력이 필요합니다.

def print_avg(numbers):
    total = 0
    for number in numbers:
        total = total + number
    avg = total / len(numbers)  # len은 배열의 길이를 구해주는 함수
    print(avg)

print_avg([1, 2, 3, 4])
print_avg([10, 20, 30, 40])

입력이 필요하지 않은 함수의 예

아래 코드의 함수 get_now는 현재 시간을 터미널에 표시해주는 기능을 하는 함수입니다. 이 함수를 중간중간 호출하면 터미널에서 코드가 실행되는 시점을 확인할 수 있습니다. 이 기능은 함수를 실행할 때마다 다른 값이 필요하지 않습니다. 따라서 입력도 필요하지 않습니다.

from datetime import datetime
def get_now():
    print(datetime.now())

출력(output)

출력은 함수 안에서 발생한 값이 함수 밖에서 필요할 때 사용한다

출력이 필요한 함수의 예

아래 코드의 함수 get_avg는 숫자 배열의 평균 값을 반환해주는 기능을 함수입니다. 위의 함수 print_avg와 어떤 차이가 있을까요?

def get_avg(numbers):
    total = 0
    for number in numbers:
        total = total + number
    avg = total / len(numbers)  # len은 배열의 길이를 구해주는 함수
    return avg

class_A = [90, 100, 80, 50]  # A반의 점수
class_B = [40, 50, 70, 80]  # B반의 점수
avg_A = get_avg(class_A)
avg_B = get_avg(class_B)
total_avg = (avg_A + avg_B) / 2 # 모든 반의 평균

get_avg에서 발생한 값인 avg를 나중에 모든 반의 평균을 구하기 위해서 코드에서 사용하고 있습니다. print_avg는 단지 터미널에 표시만 해주지만, get_avg는 발생한 avg를 코드에서 활용할 수 있습니다.

결론

함수는 항상 중복되는 코드를 제거하기 위해서 사용한다는 것과,

입력과 출력은 필요에 따라 있을 수도, 없을 수도 있다는 것을 알아주시면 되겠습니다.

 

저는 보통 아래의 절차와 같이 함수를 작성합니다.

  1. 동일한 코드의 반복이 발생한다.
  2. 반복되는 코드를 함수로 정의한다.
  3. 코드를 실행할 때마다 다른 값이 필요한지 살핀다. 있다면 매개변수(input)로 설정한다.
  4. 코드에서 발생한 값을 내가 다른 코드에서 활용하고 있는지 살핀다. 있다면 그 값을 return 한다.
  5. 만든 함수를 사용 해보고 원하는 동작과 다르다면 2,3,4를 다시 살펴본다.

별첨

  • 이 글에서 말하는 출력(output)은 화면에 출력된다는 말과 다릅니다. 함수가 뱉는 값을 말합니다.
  • 엄밀하게 말해서 모든 함수는 항상 출력 값이 있습니다. 함수를 정의할 때 return을 하지 않으면 호출 시 파이썬의 None, 자바스크립트의 undefined와 같은 값이 return 됩니다. 하지만 이 값을 굳이 코드에서 활용하지 않으므로 의미상 출력이 없는 것과 같다고 설명하였습니다.

 

Comments