IT 관련/개발(Codecademy)

자바스크립트(object 심화) this 키워드 , 오브젝트 빌트인 메소드 등

Entkommen 2023. 1. 4.
728x90

JavaScript(오브젝트 심화)

오브젝트 심화

  • how to use the this keyword.
  • conveying privacy in JavaScript methods.
  • defining getters and setters in objects.
  • creating factory functions.
  • using destructuring techniques.

This 키워드

const goat = {
  dietType: 'herbivore',
  makeSound() {
    console.log('baaa');
  },
  diet() {
    console.log(dietType);
  }
};
goat.diet(); 
// Output will be "ReferenceError: dietType is not defined"

위의 예시에서 작동이 안 되는 것이 , this 키워드를 활용하면 작동이 된다. 메서드 바깥 즉 오브젝트 내 변수에 접근이 가능해지기 때문이다.

이때 this가 참조하는 object를 calling object 라고 부른다.

const goat = {
  dietType: 'herbivore',
  makeSound() {
    console.log('baaa');
  },
  diet() {
    console.log(this.dietType);
  }
};
 
goat.diet(); 
// Output: herbivore

또 다른 상황은, 우리가 메소드를 화살표를 이용해서 정의할 때이다.

Arrow functions inherently bind , or tie, an already defined this  value to the function itself that is NOT the calling object. In the code snippet above, the value of this  is the global object , or an object that exists in the global scope, which doesn’t have a dietType  property and therefore returns undefined.

const goat = {
  dietType: 'herbivore',
  makeSound() {
    console.log('baaa');
  },
  diet: () => {
    console.log(this.dietType);
  }
};
 
goat.diet(); // Prints undefined

오브젝트 내에서 함수 생성 복습!

//ES6 축약형
const goat = {
  name: 'Billy',
  color: 'biege',
  **giveDetails(){
    console.log(`${this.name} is a ${this.color} goat.`)
  }**
}

//긴버전
const goat = {
  name: 'Billy',
  color: 'biege',
  giveDetails: function() {
    console.log(`${this.name} is a ${this.color} goat.`)
  }
}

Priavacy

다른 개발자에게 이 속성은 변경되면 안 된다 하고 알려주는 방법, 속성 이름 앞에 _ 를 붙인다.

One common convention is to place an underscore _  before the name of a property to mean that the property should not be altered. Here’s an example of using _  to prepend a property.

다만 이것은 관습일 뿐이기 때문에 _가 달린 속성을 호출해서 변경하고 이용하는 것이 가능하다.

const bankAccount = {
  _amount: 1000
}

//예를들면

bankAccount._amount = 20000 ;

//처럼 속성 값을 바꿀수 있다. 

Getters

const person = {
  _firstName: 'John',
  _lastName: 'Doe',
  get fullName() {
    if (this._firstName && this._lastName){
      return `${this._firstName} ${this._lastName}`;
    } else {
      return 'Missing a first name or a last name.';
    }
  }
}
 
// To call the getter method: 
person.fullName; // 'John Doe'

위 코드를 해석하다 보면 특이한 점은, get 뒤에 놓인 메소드를 호출하는데 괄호를 안 쓴다. 즉 호출할 때는 일반 속성처럼 호출이 가능하다는 점이다.

다음과 같은 장점이 있다고 한다. (이게 특별한 장점인지 잘 모르겠어서 추가 공부 필요해 보입니다ㅠ)

  • Getter는 데이터에서 언제 속성을 가져올지를 수행한다
  • Getter는 조건문을 사용해서 조건에 따라 다른 값을 반환할 수 있다.
    • 이건 일반 메소드도 가능하지 않나? 하는 생각이 드는데 좀 알아봐야겠습니다.
  • Getter 안에서, 우리는 this를 활용해서 calling object에 접근할 수 있다.
  • 코드의 기능성이 좋아지고, 다른 개발들이 이해하기에 편해진다.

추가적으로 , getter 함수의 이름을 다른 속성이 사용할 수는 없다. 사용하고자 한다면 _ 를 속성 앞에 붙이면 된다.

Setters

setter함수는 이미 존재하는 속성에 새로운 값을 할당하기 위해 사용된다.

const person = {
  _age: 37,
  set age(newAge){
    if (typeof newAge === 'number'){
      this._age = newAge;
    } else {
      console.log('You must assign a number to age');
    }
  }
};

//사용은 다음과 같다. 마찬가지로 ()없이 호출. age에 새로운 숫자를 할당하는 것

person.age = 40;
console.log(person._age); // Logs: 40
person.age = '40'; // Logs: You must assign a number to age

의문점 : 어차피 프로퍼티에 변경을 줄 거 왜 private 하게 만들어서 , 거기에 다시 setter를 쓰는 거지?

코드카데미 답

  • 빈 문자열, null 등의 값이 입력되는 것을 방지하고 ,
  • 원하는 조건에 맞는 , 내 입맛에 맞는 데이터를 입력할 수 있다.(privitaize 한다)

Factory Functions

오브젝트들을 여러 개 찍어내고 싶을 때, 공장에서 물건을 대량으로 생산하는 것처럼 만드는 방식이 factory function 기능이다.

햄버거를 잔뜩 생산하는 공장을 표현한다고 생각해 보자. 아래와 같이 작성이 가능하다.

const hamburgerFactory = (type, sauce, numberOfPatties, sideDish) => {
  return { 
    type: type, //위에 parameter가 value 값에 들어가는 것 같다. 
    sauce: sauce, 
    numberOfPatties: numberOfPatties,
    express() {
      console.log(`Your sidedish is ${sideDish}`);
    } 
  }
};

const burgerChoice =hamburgerFactory("burger","ketchup",3,"french fries")
;
 
 burgerChoice.express();
// 출력 : 
Your sidedish is french fries

Property Value Shorthand

위의 과정을 보다 단순화시킬 수 있게 해주는 약어 버전이다.

우선 원래의 공장 함수 형식을 보자.

const monsterFactory = (name, age) => {
  return { 
    name: name,
    age: age
  }
};

위의 예시처럼, 우리가 입력한 parameter와 키네임이 다 같게 설정한다. 이것을 매번 반복하기보다는 아래처럼 쓰는 것이 간편할 것이다.

const monsterFactory = (name, age) => {
  return { 
    name,
    age 
  }
};

위 예시처럼, 속성이름을 반복해서 적을 필요가 없어진다.

Destructured Assignment

아래와 같은 object가 있을 때, object에서 특정 속성을 호출하고 싶을 때 보통 새로운 변수에 그것을 할당한 뒤 그것을 출력하는 방식으로 한다.

Desturcted Assignment는 그 과정을 단순화하기 위해서 애초에 호출 시 변수 선언을 할 때 우리가 필요로 하는 키 값을 중괄호 안에 넣어서 그 값을 바로 호출할 수 있게 하는 것이다.

아래의 예시처럼 중첩된 오브젝트가 있을 때도 활용할 수 있다. 한마디로 말하면 이 기능은 object의 한 속성을 꺼내와서 그 값을 동명의 변수에 할당하는 기능이라고 할 수 있다.

동명이 아니면 할당이 안되고, undefined가 된다.

const { name } = obj;

아래처럼 여러 속성을 한 번에 끌어와 할당하는 것도 가능하다.

**const { name, pastTime, yearsTraining } = obj;**

const Dog= {
  name: 'Chonsa',
  residence: 'Korea',
  preferences: {
    day: 'run',
    night: 'sleeping'
  }
};
const residence = Dog.residence; 
console.log(residence); // Prints 'Korea'
const { residence } = Dog; 
console.log(residence); // Prints 'Korea'
const { day } = Dog.preferences; 
console.log(day); // Prints 'run'

Built-in Object Methods

MDN 도큐멘트를 참고하여 수많은 빌트인 오브젝트 메소드를 활용할 수 있다.

예시 )

Object.keys(obj) 의 경우 오브젝트의 키 값을 모아 어레이를 반환한다.

Object.entries(obj) 의 경우 오브젝트의 키와 밸류값을 모두 어레이로 만들어 반환한다.

Object.assign(``target, ...sources) 의 경우 source 오브젝트(추가하고 싶은 obj)과 target 오브젝트(목표가 되는 오브젝트) 두 개를 합쳐서 하나로 만들어주는 메서드이다.

target이 되는 오브젝트는 수정된다. 그러므로 수정되기를 원하지 않는 오브젝트는 source 자리에 넣어야 한다.

요약

  • 메소드가 속한 오브젝트는 ‘calling object’라고 불린다.
  • this 키워드는 calling object를 참조하고, 그래서 calling object의 속성들에 접근하는 데 사용될 수 있다.
  • 메소드는 calling object의 다른 내부 속성들에 대한 접근 권한을 자동적으로 가지고 있지는 않다.
  • this의 값은 this가 어디서부터 사용되었는지에 따라 다르다.
  • arrow function은 우리가 내부의 다른 속성을 참조하고 싶으면 사용할 수 없다.
  • 자바스크립트의 오브젝트는 privacy를 위한 빌트인이 없다. 코드 관습상 _ 를 활용한다.
  • _를 활용하면 , 그것을 쓴 개발자가 이 변수는 직접적으로 변경되는 것을 원하지 않는다는 표시이다.
  • Setter 와 Getter 메소드는 보다 다양하고 세분화된 변수 설정방법을 제공한다.
  • 공장함수는 오브젝트 인스턴스(?) 들을 빠르고 반복적으로 생성하게 해 준다.
  • object destructuring을 사용하는 여러 방법이 있다. 하나는 축약형이고, 하나는 destructured assignment이다.
728x90