TIL 8일차 (20230103)

박세연·2024년 1월 3일

TIL

목록 보기
7/70

오늘은 알고리즘 강의 첫날!

더 많은 사람들이 있다보니 다양한 풀이 방식을 볼 수 있어서 좋았다. 특히 cnt++로 수를 점차 증가시키는 것, for만 쓰지 말고 while도 써보는 연습을 해보자고 반성할 수 있었다.


✨ 실행컨텍스트(스코프, 변수, 객체, 호이스팅)

실행 컨텍스트 객체의 실체(담기는 정보)

  • VariableEnvironment(VE): snapshot 가짐

  • LexicalEnvironment(LE): 실시간으로 변경사항 반영(코드 실행x)
    -> record, 호이스팅

    function a (x) {
    		console.log(x);
    		var x;
    		console.log(x);
    		var x = 2;
    		console.log(x);
      }
    		a(1);

    function a () {
    		var x;
    		var x;
    		var x;
    
    		x = 1;
    		console.log(x);
    		console.log(x);
    		x = 2;
    		console.log(x);
    		}
    		a(1);

    의 출력은 모두 1, 1, 2이다.
    마찬가지로

    function a () {
    		console.log(b);
    		var b = 'bbb';
    		console.log(b);
    		function b() { }
    		console.log(b);
    		}
    		a();

    function a () {
    		var b; // 변수 선언부 호이스팅
    		function b() { } // 함수 선언은 전체를 호이스팅
    
    		console.log(b);
    		b = 'bbb'; // 변수의 할당부는 원래 자리에
    
    		console.log(b);
    		console.log(b);
    		}
    		a();

    역시 똑같은 b함수, ‘bbb’, ‘bbb’가 출력된다.


    -> 함수 선언문, 함수 표현식

    1. 함수 선언문: function 00(){} 정의, 할당 명령이 없는 경우
    2. 익명 함수 표현식: var b = function () {}
    3. 기명 함수 표현식: var c = function d () {}
      -> 이때 c()는 실행되지만 d()는 에러가 뜬다.
      (d()는 c()안에서 재귀적으로 호출될 때만 사용 가능하므로) ⭐ 함수 선언문으로 짜면 hoisting에 의해 함수 전체가 위쪽으로 가버림.
      ⭐ 함수 표현문으로 해야 의도한 위치에 있으므로 협업 시 함수 표현문을 활용해야함
      -> 스코프, 스코프 체인, outer(outerEnvironmentReference)
    4. 스코프: 식별자에 대한 유효 범위
    5. 스코프 체인: 식별자의 유효 범위를 안에서부터 바깥으로 차례로 검색해나가는 것
    6. outer: 스코프 체인이 가능토록 하는 것(외부 환경의 참조 정보), 자신이 선언된 시점의 LE를 참조하므로 가장 가까운 요소부터 차례대로 접근
  • ThisBinding: this 식별자가 봐야할 객체(바로 아래에서 정리)

This 정의, 활용 방법, 바인딩, call, apply, bind

(1) 상황에 따라 달라지는 this

  • 전역 공간에서는 전역 개체를 가리킴
  • 함수는 대상 객체 없이 독립적으로 기능을 수행하지만 메서드는 호출 대상 객체가 있다.(ex. 00.(.또는 대괄호)메서드())
  • 함수 내부에서의 this: 실행 컨텍스트를 활성화할 당시 this가 지정되지 않은 경우 전역 객체를 의미
  • 메서드의 내부 함수에서의 this: 함수이므로 전역객체
var obj1 = {
	outer: function() {
		console.log(this); // (1)
		var innerFunc = function() {
			console.log(this); // (2), (3)
		}
		innerFunc();

		var obj2 = {
			innerMethod: innerFunc
		};
		obj2.innerMethod();
	}
};
obj1.outer();

에서 (1)은 obj, (2)는 전역, (3)은 obj2인데 점이나 대괄호의 유무로 메서드인지 함수인지 알 수 있고, 이를 통해 this가 무엇인지 알 수 있다.

  • 메서드 내부 함수에서의 this 우회
    1. 변수(ex. self) 활용
    2. 화살표 함수: this를 바인딩하지 않음. 따라서 this는 상위값이 유지됨
    3. 콜백 함수 호출 시 그 함수 내부의 this: 콜백함수를 넘겨받은 함수나 메서드가 정한 규칙에 따라 값이 결정됨. 넘겨받은 함수가 별도로 this를 지정한 경우 그 대상을 참조함.

(2) 명시적 this 바인딩
2-1. call 메서드

var func = function (a, b, c) {
	console.log(this, a, b, c);
};

// no binding
func(1, 2, 3); // Window{ ... } 1 2 3

// 명시적 binding
// func 안에 this에는 {x: 1}이 binding돼요
func.call({ x: 1 }, 4, 5, 6}; // { x: 1 } 4 5 6

2-2. apply 메서드
: this에 binding할 객체는 똑같이 넣어주고 나머지 부분만 ⭐배열 형태로 넘겨준다.

var func = function (a, b, c) {
	console.log(this, a, b, c);
};
func.apply({ x: 1 }, [4, 5, 6]); // { x: 1 } 4 5 6

var obj = {
	a: 1,
	method: function (x, y) {
		console.log(this.a, x, y);
	}
};

obj.method.apply({ a: 4 }, [5, 6]); // 4 5 6

2-3. call, apply 메서드의 활용

  • 반드시 유사배열({})에 length가 있어야한다, 이때 번호는 0부터 시작해서 1씩 증가해야한다.
  • 아래 메서드들은 모두 var (array명) = ~~으로 사용하도록 할것
  • Array.prototype.slice.call() 메서드
  • Array.from() 메서드
  • 생성자 내부에서 다른 생성자를 호출
function Person(name, gender) {
	this.name = name;
	this.gender = gender;
}
function Student(name, gender, school) {
	Person.call(this, name, gender); // 여기서 this는 student 인스턴스!
	this.school = school;
}
function Employee(name, gender, company) {
	Person.apply(this, [name, gender]); // 여기서 this는 employee 인스턴스!
	this.company = company;
}
  • 여러 인수를 묶어 하나의 배열로 전달할 때 apply 적용

2-4. bind 메서드
: 즉시 호출하지 않고 넘겨받은 this 및 인수들을 바탕으로 새로운 함수 반환, 부분 적용 함수 구현할 때 용이

2-5. 화살표 함수의 예외 사항
: 함수 내부에는 this의 할당과정이 아예 없으며, 접근하고자 하면 가장 가까운 this에 접근

profile
배워나가는 중

0개의 댓글