# 화살표함수
저는 gitlab FE 인터뷰 자료의 javascript 를 다 읽어보고 공부를 하고 있습니다. 몇몇 스터디 원분들께서는 그래서 제가 정리한 공부의 문맥이 이해가 안되실 수 있습니다. 문맥의 이해가 안되실땐, 궁금하면 저한테 질문을 주시거나. 아니면 넘어가고 나중에 다시 이해하셔도 됩니다.
# 개요
- this, arguments, super, new.target 을 바인딩 하지 않는다. TODO about
- 익명함수 이기 때문에, 메서드가 아닌 함수에 사용하는 것이 적절하다.
- 익명 함수이기 때문에 생성자로 사용할 수 없다.
# 화살표 함수는 단순히 짧게 쓰는 용도로만 사용되지 않는다.
- arr.forEach(func), setTimeout(func) 같은 func 를 생성하고 여기에 전달하는 것이 자연스럽다.
- 그런데 외부에다 생성을 하여 전달하게 되면 함수의 컨텍스트를 잃어버릴 수 있는데, 이때 화살표 함수를 사용한다.
new 생성자로 생성한 Person 객체의 this 는 자신의 인스턴스로 정의된다.
그러나 setInterval 내의 인수의 콜백함수의 this 는 비엄격모드에서 전역을 가리킨다.
function Person() {
this.age = 0;
setInterval(function growUp () {
this.age++
}, 1000)
}
var p = new Person();
2
3
4
5
6
7
변수로 this 를 정의해 콜백 함수에서 사용한다.
function Person() {
var that = this;
that.age = 0;
setInterval(function growUp() {
that.age++;
}, 1000);
}
2
3
4
5
6
7
8
# 문법
- 객체 리터럴 식을 반환
params => ({foo: bar})
- 나머지 매개변수 지원
(param1, param2, ...rest) => { statements }
1 - 기본 매개변수 지원
(param1 = defaultValue1, param2, ... , paramN = defaultValueN) => { statements }
1 - 매개변수 목록 내 구조분해 지원
var f = ([a, b] = [1, 2], {x: c} = { x: a + b}) => a + b + c;
1
# 동적 화살표 함수
let age = prompt('나이를 알려주세요.', 18);
let welcome = (age < 18) ?
() => alert('안녕') :
() => alert('안녕하세요!');
welcome();
2
3
4
5
6
# 파싱 순서
일반 함수와 비교했을 때 연산자 우선순위가 다르게 반응한다.
let callback;
callback = callback || function () {};
callback = callback || () => {}; // SyntaxError: invalid arrow-function arguments
callback = callback || (() => {});
2
3
4
TODO 3번줄을 디버깅해보자
# 화살표 함수에는 'this' 가 없다.
화살표 함수 본문에서 this 에 접근하면, 외부에서 값을 가져온다.
화살표 함수의 this 는 showList() 의 this 와 같다.
let group = {
title: '1모둠',
students: ["보라", "호진", "지민"],
showList() {
this.students.forEach(
student => alert(this.title + ': ' + student)
);
}
};
group.showList();
2
3
4
5
6
7
8
9
10
forEach 에 전달되는 this 는 undefined 가 된다.
콜백 함수를 호출하는 함수의 내부를 알아야 this 를 알수 있다.
let group = {
title: '1모둠',
students: ["보라", "호진", "지민"],
showList() {
this.students.forEach(function(student) {
// TypeError: Cannot read property 'title' of undefined
alert(this.title+': '+student);
})
}
}
group.showList();
2
3
4
5
6
7
8
9
10
11
콜백 함수를 호출하는 함수의 두번째 인자에 this 를 명시해 줄 수 있다.
let group = {
title: '1모둠',
students: ["보라", "호진", "지민"],
showList() {
this.students.forEach(function(student) {
// TypeError: Cannot read property 'title' of undefined
alert(this.title + ': '+student);
}, group)
}
}
group.showList();
2
3
4
5
6
7
8
9
10
11
# 화살표 함수는 new 와 함께 실행할 수 없다.
- this 가 없기 때문에 화살표 함수는 생성자 함수로 사용할 수 없다.
var Foo = () => {};
var foo = new Foo(); // TypeError: Foo is not a constructor
2
# 화살표 함수엔 'arguments' 가 없다.
function defer (f, ms) {
return function() {
setTimeout(() => f.apply(this, arguments), ms);
}
}
function sayHi(who) {
alert('안녕, ' + who);
}
let sayHiDeferred = defer(sayHi, 2000);
sayHiDeferred('철수');
2
3
4
5
6
7
8
9
10
this 값과, arguments 정보를 함께 실어 호출을 포워딩해 주는 데코레이터를 만들때 유용하다.
데코레이터 defer(f, ms) 는 함수를 인자로 받고 이 함수를 래퍼로 감싸 반환한다.
함수 f 는 ms 밀리초 이후에 호출된다.
화살표 함수를 동일한 기능을 하려면, setTimeout 함수의 콜백함수에서 사용할 변수를 만들어 줘야한다.
function defer(f, ms) {
return function(...args) {
let ctx = this;
setTimeout(function() {
return f.apply(ctx, args)
})
}
}
2
3
4
5
6
7
8
화살표 함수의 arguments 객체 대신에 나머지 매개변수를 사용한다.
function foo(n) {
var f = (...args) => args[0] + n;
return f(2);
}
f(1);
2
3
4
5
# super 가 없다.
TODO 클래스 상속
화살표 함수와 this - 강사님 예제 고급 특징
# 엄격 모드와의 관계
this가 렉시컬임을 감안하면 this 에 관한 엄격모드 규칙은 무시된다.
var f = () => {'use strict'; return this;}
f() === window;
2
# 메서드로 사용되는 화살표 함수
'use strict'
var obj = {
i: 10,
b: () => console.log(this.i, this),
c: function() {
console.log(this.i, this)
}
}
2
3
4
5
6
7
8
9
일반메서드 c 는 obj 가 this
obj.c(); // 10, Object { ... }
화살표 메서드 b 는 전역 실행문맥에서 실행되고 있으므로 this 는 Window 가 된다.
obj.b(); // undefined, Window
접근자 프로퍼티의 함수로 사용되는 화살표 함수
'use strict';
var obj = {
a: 10
};
Object.defineProperty(obj, 'b', {
get: () => {
console.log(this.a, typeof this.a, this); // undefined 'undefined' Window {...} (or the global object)
return this.a + 10; // returns 'undefined'
}
})
2
3
4
5
6
7
8
9
10
11
# prototype 속성이 없다.
var Foo = () => {};
console.log(Foo.prototype); // undefined
2
# yield 키워드를 사용할 수 없다.
화살표 함수는 생성기(generator) 로서 사용될 수 없다.
화살표 함수의 중첩 함수 내에서는 사용가능하다.