javaScript/js.function

함수

1. 함수란?

input을 받아서 output을 내보내는 일련의 과정
함수는 함수 정의(Function definition)를 통해 생성한다.
JS의 함수는 다양한 방법으로 정의할 수 있다.
함수의 정의만으로 함수가 실행되지 않는다. 인수 -> 매개변수를 통해 함수에게 전달하면서 함수의 실행을 명시적으로 지시해야한다.
이를 함수호출(Function call/invoke)이라 한다.

1
2
3
4
5
// f(x, y) = x + y
function add(x, y) { //함수 정의
return x + y;
}
add(2, 5); //7 //함수 호출

함수를 호출하면 코드 블록에 담긴 문들이 일괄적으로 실행되고 반환값을 반환한다.

2. 함수의 사용 이유

  • 동일한 작업을 반복적으로 수행한다면, 미리 정의된 함수를 재사용하는 것이 효율적이다.
    함수는 얼마든지 호출할 수 있으므로 코드의 재사용의 측면에서 매우 유용하다.
  • 함수는 유지보수의 편의성을 높이고 실수를 줄여 코드의 신뢰성을 높이는 효과가 있다.
  • 코드의 가독성을 향상시킨다. (객체타입의 값이라 식별자를 붙일 수 있음)

3. 함수 리터럴

JS의 함수는 객체 타입의 값
함수 리터럴은 function 키워드, 함수 이름, 매개변수, 함수 몸체로 구성된다.

1
2
3
4
// 변수에 함수 리터럴을 할당
var add = function add(x, y) {
return x + y;
};

함수는 호출할 수 있지만, 일반 객체는 호출할 수 없다.

함수 객체만의 고유한 프로퍼티를 갖는다.

함수이름

  • 함수 이름은 식별자. 네이밍 규칙을 준수해야한다.
  • 함수 이름은 함수 몸체 내에서만 참조할 수 있는 식별자이다.
  • 함수 이름은 생략 가능하다.

매개변수 목록

  • 0개 이상의 매개변수를 소괄호로 감싸고 쉼표로 구분한다.
  • 함수 호출문의 인수가 순서대로 할당된다. 매개변수 목록은 순서에 의미가 있다.
  • 함수 몸체 내에서 변수와 동일하게 취급된다. 변수와 마찬가지로 식별자 네이밍 규칙을 준수해야한다.

함수 몸체

  • 함수 몸체는 함수 호출에 의해 실행된다.
  • 함수가 호출되었을 때 일괄적으로 실행될 문들을 하나의 실행 단위로 정의한 코드 블록이다.

4. 함수 정의

함수를 호출하기 이전에 인수를 전달받을 매개변수와 실행할 문들, 그리고 반환할 값을 지정하는 것을 말한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
// 함수 선언문
function add(x, y) {
return x + y;
}

// 함수 표현식
var add = function (x, y) {
return x+y;
};

//function 생성자 함수
var add = new Function('x', 'y', 'return x + y');

//화살표 함수 (ES6에 추가)
var add = (x, y) => x + y;

4.1 함수 선언문

  • 함수 선언문은 리터럴과 형태가 동일하다. 함수 선언문은 함수 이름을 생략할 수 없다.
  • 함수 선언문은 표현식이 아닌 문이다. (선언문이기 때문에 undefined를 출력한다.)
  • 표현식이 아닌 문은 변수에 할당할 수 없지만, 함수 선언문은 변수에 할당하는 것 처럼 보인다.
  • JS 엔진은 함수 이름과 동일한 이름의 식별자를 암묵적으로 생성하고 생성된 함수 객체를 할당한다.
  • 함수는 함수 이름으로 호출하는게 아니라 함수 객체를 가리키는 식별자로 호출한다.

자바스크립트 엔진은 함수선언문을 함수 표현식으로 변환하여 함수 객체를 생성한다고 생각할 수 있다.

4.2 함수 표현식

  • 자바스크립트의 함수는 일급 객체 (함수를 값처럼 자유롭게 사용할 수 있음)

  • 일급 객체이므로 함수 리터럴로 생성한 함수 객체를 변수에 할당할 수 있다.

  • 함수 리터럴의 함수 이름은 생략할 수 있다. (생략하는 것이 일반적, 익명 함수)

    함수 선언문과 함수 표현식의 차이. 함수 생성 시점과 호이스팅

4.3 함수 생성 시점과 함수 호이스팅

함수 선언문과 함수 표현식은 함수 생성 시점이 다르다.

  • 함수 선언문으로 함수를 정의하면 런타임 이전에 함수 객체가 먼저 생성된다.
    자바스크립트 엔진은 함수 이름과 동일한 이름의 식별자를 암묵적으로 생성하고 함수 객체를 할당
  • 함수 선언문을 통해 암묵적으로 생성된 식별자는 함수 객체로 초기화

함수 표현식은 변수 할당문의 값이 함수 리터럴인 문

  • 함수 표현식은 변수 선언문과 변수 할당문을 한번에 기술한 축약 표현과 동일하게 동작한다.
  • 변수 할당문의 런타임에 평가되므로 함수 표현식의 함수 리터럴도 할당문이 실행되는 시점에 평가되어 함수 객체가 된다.
  • 함수 표현식으로 함수를 정의하면 함수 호이스팅이 발생하는 것이 아니라 변수 호이스팅이 발생한다.
  • 함수 표현식 이전에 함수를 참조하면 타입에러가 발생한다.
  • 함수 표현식으로 정의한 함수는 반드시 함수 표현식 이후에 참조 또는 호출해야 한다.

4.4 Function 생성자 함수 (빌트인 함수) (Constructor Function)

  • 생성자 함수는 객체를 생성하는 함수.
  • Function 생성자 함수로 생성한 함수는 클로저를 생성하지 않는 등, 함수 선언문이나 함수 표현식으로 생성한 함수와 다르게 동작한다.

4.5 화살표 함수

  • 화살표 함수는 항상 익명 함수로 정의한다.
  • 생성자 함수로 사용할 수 없으며 기존의 함수와 this 바인딩 방식이 다르고, prototype 프로퍼티가 없으며 arguments 객체를 생성하지 않는다.

5. 함수 호출

  • 함수는 함수를 가리키는 식별자와 한 쌍의 소괄호인 함수 호출 연산자로 호출한다.
  • 함수 호출 연산자 내에는 0개 이상의 인수(argument)를 쉼표로 구분하여 나열한다.
  • 호출하면 현재의 실행 흐름을 중단, 호출된 함수로 컨트롤을 넘긴다.
    인수 -> 매개변수 할당 , 함수 몸체의 문들이 실행

5.1 매개변수와 인수

함수 외부에서 함수 내부로 필요 값을 전달할 필요가 있는 경우 인수(외부) -> 매개변수(내부)

  • 인수는 값으로 평가될 수 있는 표현식이어야 하며, 함수를 호출할 때 지정하며 개수와 타입에 제한이 없다.
  • 매개변수는 함수를 정의할 때 선언하며 함수 몸체 내부에서 변수와 동일하게 취급한다.
    (함수가 호출되면 함수 몸체 내에 암묵적으로 매개변수가 생성되고, undefined로 초기화된 이후 인수가 순서대로 할당된다.) 호출될 때마다 이 단계를 거침
  • 매개변수는 함수 몸체 내부에서만 참조할 수 있고 함수 몸체 외부에서는 참조할 수 없다.
    (스코프는 함수 내부이다.)
  • 매개변수와 인수의 개수를 체크하지 않는다.
    • 인수가 부족하면 할당되지 않은 매개변수의 값은 undefined
    • 초과된 인수는 무시된다. 모든 인수는 암묵적으로 arguments 객체의 프로퍼티로 보관된다.

5.2 인수 확인

  • 자바스크립트 함수는 매개변수와 인수의 개수가 일치하는지 확인하지 않는다.
  • 자바스크립트 함수는 매개변수의 타입을 사전에 지정할 수 없다.
    따라서 함수를 정의할 때 적절한 인수가 전달되었는지 확인이 필요하다.

5.3 매개변수의 최대 개수

  • 이상적인 매개변수 개수는 0개이며 적을 수록 좋다.
  • 3개 이상을 넘지 않는 것을 권장한다. (그 이상의 매개변수가 필요하다면 하나의 매개변수를 선언하고 객체를 인수로 전달받는 것이 유리하다.)
  • 매개변수의 개수나 순서가 변경되면 함수의 호출 방법도 변경되므로 함수를 사용하는 코드 전체가 영향을 받는다. (유지보수성도 나빠진다.)

5.4 반환문

  • 실행 결과를 함수 외부로 반환(return)
  • 반환문은 함수의 실행을 중단하고 함수 몸체를 빠져나간다.
  • 반환문 이후에 다른 문이 존재하면 그 문은 무시된다.
  • return 키워드 뒤에 지정한 값을 반환한다. 명시적을 지정하지 않으면 undefined가 반환된다.
  • 반환문을 생략할 수 있다. 함수는 마지막 문까지 실행한 후 암묵적으로 undefined를 반환한다.

6. 참조에 의한 전달과 외부 상태의 변경

함수의 매개변수에 값을 전달하는 방식 Call by value, Call by reference
동작 방식은 값에 의한 전달, 참조에 의한 전달

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
//primitive은 원시값, obj는 객체를 전달받는다.
function changeVal(primitive, obj) {
primitive += 100;
obj.name = 'Kim';
}

//외부 상태
var num = 100;
var person = { name: 'Jung'};

console.log(num); // 100
console.log(person); // {name: 'Jung'}

//원시값은 값 자체가 복사되어 전달되고 객체는 참조값이 복사되어 전달
changeVal(num, person);

원시 값은 원본이 훼손되지 않는다. 객체는 원본이 훼손된다.

  • 원시 타입 인수는 값 자체가 복사되어 매개변수에 전달되기 때문에 원본은 훼손되지 않는다. side-effect가 없다
  • 객체 타입 인수는 참조값이 복사되어 매개변수에 전달되기 때문에 원본이 훼손된다. side-effect 발생
  • 객체를 불변 객체로 만들어 사용해서 외부상태가 변경되는 side-effect를 없앨 수 있다.

7. 다양한 함수의 형태

7.1 즉시실행함수(IIFE)

  • 즉시 실행 함수는 단 한번만 호출되며 다시 호출할 수 없다. (첫번째 메인 페이지에 사용)
  • 익명 함수를 사용하는 것이 일반적이다.
    1
    2
    3
    4
    5
    (function () {
    var a = 3;
    var b = 5;
    return a + b;
    }());
  • 즉시 실행 함수는 반드시 그룹 연산자()로 감싸 주어야 한다.
  • 그룹 연산자로 함수를 묶은 이유는 먼저 함수를 평가하여 함수 객체를 생성하기 위함이다.

7.2 재귀 함수(recursive function)

  • 함수가 자기 자신을 호출하는 것을 재귀 호출이라 한다.
  • 팩토리얼은 재귀 호출로 간단히 구현할 수 있다.
  • 재귀 호출을 멈출 수 있는 탈출 조건을 반드시 만들어야 한다.
  • 함수 호출은 반드시 함수를 가리키는 식별자로 해야 한다.
  • 재귀 함수는 for 문이나 while 문으로 구현 가능하다.

7.3 중첩 함수(nested function)

  • 함수 내부에 정의된 함수를 중첩함수 또는 내부 함수(inner function)라 한다.
  • 중첩 함수를 포함하는 함수를 외부 함수(outer function)라 한다.
  • 일반적으로 중첩 함수는 자신을 포함하는 외부 함수를 돕는 헬퍼 함수 역할을 한다.

7.4 콜백 함수(Callback function)

고차함수(Higher-Order Function, HOF)의 인자로 넘겨지는 함수.
콜백 함수는 고차함수 내에서 수행된다. (내용 추가하기)

7.5 순수 함수와 비순수 함수

순수 함수 - 부수효과가 없는 함수(외부 상태를 변경시키는)
비순수 함수 - 부수효과가 있는 함수
함수형 프로그래밍은 순수 함수를 통해 부수 효과를 최대한 억제하여 오류를 피하고 프로그램의 안정성을 높이려는 노력의 한 방법이라고 할 수 있다.

You forgot to set the qrcode for Alipay. Please set it in _config.yml.
You forgot to set the qrcode for Wechat. Please set it in _config.yml.
You forgot to set the business and currency_code for Paypal. Please set it in _config.yml.
You forgot to set the url Patreon. Please set it in _config.yml.
Your browser is out-of-date!

Update your browser to view this website correctly. Update my browser now

×