모던 자바스크립트 Deep Dive Ch18~20

Jayde·2023년 2월 12일
0

2023-1 studyJs

목록 보기
5/7
post-thumbnail

Ch18. 일급 객체

<조건>
1. 무명의 리터럴로 생성할 수 있음(런타임에 생성 가능)
2. 변수나 자료구조에 저장 가능
3. 함수의 매개변수에 전달 가능
4. 함수의 반환값으로 사용 가능
함수가 일급 객체다 = 함수를 객체처럼 사용할 수 있다

  • 함수 객체의 프로퍼티
    1. arguments
    함수 호출 시 전달된 이수들의 정보를 담고 있는 순회 가능한 유사 배열 객체
    함수 내부에서 참조하도록 함
    매개변수와 인수의 개수 확인 X(매개변수를 undefined로 초기화 한 후 인자 할장 → 적으면 undefined, 초과하면 뒤에꺼 무시되지만 argument 객체 프로퍼티로 보관되긴 함)
    가변 인자 함수 구현에 유용(유사 배열 객체니까 길이만큼 for문 순회 가능)

    유사 배열 객체
    length 프로퍼티를 가져 for문으로 순회 가능한 객체
    배열 메서드 사용하려면 Function.prototype.apply, Function.prototype.call을 간접호출 해야함

    2. caller
    비표준 프로퍼티
    함수 자신을 호출한 함수를 가리킴

    3. length
    함수를 정의할 때 선언한 매개변수의 개수
    argumentslength는 인자의 개수를 가리킨다는 차이가 있음

    4. name
    ES6부터 함수 객체를 가리키는 식별자로 값을 가짐

    5. __proto__, prototype
    proto
    [[Prototype]] 내부 슬록이 가리키는 프로토타입 객체에 접근하기 위해 사용하는 접근자 프로퍼티(간접)
    prototype
    생성자 함수로 호출할 수 있는 함수 객체(constructor만이 소유)


Ch19. 프로토타입

  • 객체지향 프로그래밍
    : 프로그램을 여러 개의 독립적 단위(=객체의 집합)으로 표현하는 프로그래밍 패러다임
    속성을 통해 프로그램을 인식하거나 구별함
    추상화 : 다양한 속성 중 프로그램에 필요한 속성만 간추려 내어 표현하는 것
    객체 :속성을 통해 여러 개의 값을 하나의 단위로 구성한 복합적 자료구조
    객체 지향에서는 객체의 상태와 동작을 하나의 논리적 단위로 묶어 생각함(상태 = 프로퍼티, 동작 = 메서드)
    다른 객체와 관계성을 가질 수도 있음(≒상속)

  • 상속과 프로토타입
    프로토타입 기반 상속 구현 → 불필요한 중복 제거

  • 프로토타입 객체
    개체 간 상속을 구현하기 위해 사용
    모든 객체는 [[Prototype]]이라는 내부 슬롯을 가지며 이 냅 슬롯의 값은 프로토타입의 참조이거나 null임. [[Prototype]]에 저장되는 프로토타입은 객체 생성 방식에 따라 결정됨
    모든 객체는 하나의 프로토타입을 갖고 모든 프로토타입은 생성자 함수와 연결되어 있음.
    프로토타입과 생성자 함수는 언제나 쌍으로 존재

  • __proto__ 접근자 프로퍼티
    __proto__를 통해 자신의 프로토타입인 [[Prototype]] 내부슬롯에 접근 가능
    상속을 통해 사용
    접근자 프로퍼티를 이용하는 이유 : 상호 참조에 의한 프로토타입 체인 생성 방지
    모든 경우에 사용할 수 있지 않음(프로토타입을 상속받지 않은 경우도 있으므로)
    Object.getPrototypeOf : 프로토타입 참조를 취득하고 싶을 때
    Object.setPrototypeOf : 프로토타입을 교체하고 싶을 때

  • prototype 프로퍼티
    생성자 함수가 생성할 객체의 프로토타입을 가리킴
    __proto__와 prototype은 결국 동일한 프로토타입을 가리키나 사용 주체가 다름

구분소유사용 주체사용 목적
__proto__모든 객체프로토타입의 참조모든 객체객체가 자신의 프로토타입에 접근/교체를 위해
prototypecostructor프로토타입의 참조생성자 함수생성자 함수가 자신이 생성학 객체의 프로토타입을 할당하기 위해

  • 프로토타입의 생성 시점
    (빌트인)생성자 함수가 생성되는 시점에 더불어 생김

  • 객체 생성 방식과 프로토타입
    추상 연산 OrdinaryObjectCreate에 전달되는 인수에 의해 결정되며, 여기서 인수는 객체가 생성되는 시점에 객체 생성 방식에 의해 결정됨

    1. 객체 리터럴
    객체 생성시 Object.prototype이 전달됨.
    객체 리터럴에 의해 생성된 객체는 Object.prototype을 프로토타입으로 갖게 되어 상속 받음.

    2. Object 생성자 함수
    new Object() 호출 시 Object.prototype이 전달됨.
    객체리터럴과 동일

    3. 생성자 함수
    new연산자라 함께 호출 시 prototype 프로퍼티에 바인딩 되어 있는 객체가 전달됨.
    연결이 생성되는건 1,2랑 동일하나 빌트인 메서드가 없고 constructor만 있음.
    대신 생성자.prototype에 프로퍼티 추가하여 하위 객체가 상속받을 수 있도록 구현 가능

  • 프로토타입 체인
    js는 객체의 프로퍼티에 접근하려고 할 때 해당 객체에 접근하려는 프로퍼티가 없으면 부모 역할 프로토타입의 프로퍼티를 순차적으로 검색하고 이걸 프로토타입 체인이라 함
    프로토타입 체인의 최상위에 위치하는 객체는 언제나 Object.prototype
    프로토타입 체인은 검색을 위한 거라고 보면 됨(tls 인증서 프로토콜이랑 비슷한듯?)
    스코프 체인은 식별자 검색을 위한 거
    프로토타입 체인과 스코프 체인은 서로 협력해 식별자와 프로퍼티를 검색함

  • 오버라이딩과 프로퍼티 섀도잉
    : 프로토타입 메소드와 동일한 이름의 프로퍼티를 인스턴스에 추가하면 오버라이딩 되어 상속관계에 의해 프로토타입 메소드의 프로퍼티가 가려지는 현상

  • 프로토타입 교체
    프로토타입은 임의의 다른 객체로 변경 가능 → 객체 간 상속 관계 동적 변경 가능
    생성자 함수 또는 인스턴스에 의해 교체 가능
    생성자 함수로 교체하면 생성자 함수의 prototype 프로퍼티가 교체된 프로토타입을 가리킴
    인스턴스로 교체하면 생성자 함수의 prototype 프로퍼티가 교체된 프로토타입을 가리키지 않음
    프로토타입 교체를 통한 객체 간 상속 관계 변경은 꽤나 번거로움 ∴직접 하지 않는 게 좋음

  • instanceof 연산자
    우변의 생성자 함수의 prototype에 바인딩된 객체가 좌변의 객체 프로토타입 체인 상에 존재 == true
    프로토타입이 교체되어 constructor 프로퍼티와 생성자 함수 간 연결이 파괴되어도 생성자 함수의 prototype 프로퍼티와 프로토타입 간 연결은 그대로 → instaceof엔 영향 X

  • 직접 상속
    1. Object.create
    첫 번째 매개변수: 생성할 객체의 프로토타입으로 지정할 객체
    두 번째 매개변수(옵션): 생성할 객체의 프로퍼티 키와 프로퍼티 디스크립터 객체로 이뤄진 객체 전달
    체인 종점에 위치하는 객체도 생성 가능 = Object.prototype 빌트인 메서드 이용 불가능
    <장점>
    1.new 연산자가 없어도 객체 생성 가능
    2.프로토타입을 지정하면서 객체 생성 가능
    3.객체 리터럴에 의해 생성된 객체도 상속 가능
    2. 객체 리터럴 내부에서 __proto__

  • 정적 프로퍼티/메서드
    : 생성자 함수로 인스턴스를 생성하지 않아도 참조/호출할 수 있는 프로퍼티/메서드
    생성자 함수가 생성한 인스턴스로 참조/호출 불가

  • 프로퍼티 존재 확인
    1. in 연산자
    : 객체 내에 특정 프로퍼티 존재 여부 확인(확인 대상 객체가 상속받은 모든 프로토타입 프로퍼티 포함)
    key in object
    in 대신 Reflect.has도 사용 가능(얘는 상속 불포함)
    Reflect.has(object.hasOwnProperty)

  • 프로퍼티 열거
    1. for ... in 문
    for (변수 선언문 in 객체) {}
    프로퍼티 개수만큼 순회하며 변수 선언문에서 선언한 변수 프로퍼티 키 할당
    열거할 수 없도록 정의되어 있는 프로퍼티 제외 상속 포함
    프로토타입 체인 상 존재하는 모든 프로토타입의 프로퍼티 중 프로퍼티 어트리뷰트 [[Enumerable]] 값이 true인 프로퍼티를 순회하며 열거
    키가 Symbol인 프로퍼티는 제외
    열거할 때 순서 보장 X(하지만 대부분의 모던 브라우저는 순서 보장)
    2. Object.keys/values/entries 메서드
    객체 자신의 고유 프로퍼티만 열거
    Obejct.keys : 객체 자신의 열거 가능한 프로퍼티 키를 배열로 반환
    Object.values : 객체 자신의 열거 가능한 프로퍼티 값을 배열로 반환
    Object.entries : 객체 자신의 열거 가능한 프로퍼티 키와 값을 쌍을 배열의 배열에 담아 반환


Ch20. strict mode

: js 문법을 좀 더 엄격히 적용하여 오류를 발생시킬 가능성이 높거나 자바스크립트 엔진의 최적화 작업에 문제를 일어킬 수 있는 코드에 대해 명시적 에러를 발생시키는 모드

ESLint : 정적 분석 기능을 통해 잠재적 오류까지 찾아내고 원인을 리포팅 해줌

  • 적용
    전역이나 함수의 선두에 'use strict'; 추가

  • 주의
    1. 전역에 적용하지 않기
    전역에 적용하면 스크립트 단위로 적용됨 → strict mode 스크립트와 non-strict mode 스크립트가 혼용되어 오류 발생 가능성이 있음
    ∴ 즉시 실행 함수로 스크립트 전체를 감싸서 즉시 실행 함수의 선두에 strict mode 적용

    (function(){
        'use strict';
        //코드..
    }());

    2. 함수 단위로도 적용하지 않기
    혼용 바람직하지 않음
    strict mode가 적용된 함수가 참조할 함수 외부의 컨텍스트에 strict 모드 적용 X → 문제 발생

  • 발생시키는 에러
    1. 암묵적 전역
    선언하지 않은 변수 참조 시 ReferenceError 발생
    2. 변수, 함수, 매개변수의 삭제
    delete 연산자로 변수, 함수, 매개변수 삭제 시 SyntaxError 발생
    3. 매개변수 이름의 중복
    중복된 매개변수 이름 사용 시 SyntaxError 발생
    4. with문 사용
    with문 사용 시 SyntaxError 발생
    with문은 전달된 객체를 스코프 체인에 추가하는데 객체 이름을 생략할 수 있어 코드가 간단해지나 성능과 가독성에 문제를 일으킴

  • 발생시키는 변화
    1. 일반 함수의 this
    strict mode에서 함수를 일반 함수로 호출하면 this에 undefined가 바인딩됨.
    생성자 함수가 아닌 일반 함수에서 this를 사용할 필요가 없기 때문
    2. arguments 객체
    매개변수에 전달된 인수를 재할당해 변경해도 arguments 객체에 반영 X

profile
가장 높이 빛난 별 잡아보일게

0개의 댓글