본문 바로가기
코딩일기/TIL

TIL-3 ES 6 문법과 일급객체로서의 함수 그리고 Map과 Set

by 2pro.e_pro 2024. 6. 18.
728x90
반응형

TIL-3 ES6 문법과 일급객체로서의 함수 그리고 Map과 Set

prologue. 배운걸 반복하는데 왜 어렵지..?

이번 포스팅에서는 2주차 과정에서 배운 개념들을 정리하려고 한다.

어라? 앞서 1주차에도 배운 개념들이 반복되네?

 

와 신난다 ~! 도 잠시..

왜 어렵지??... 😃..

 

 

1. ES 6 (ECMAScript 6)

ECMAScript 6는 JavaScript의 버전 중 하나로 2015년에 발표되었으며 

ES 6 버전 업데이트에서는 기존 ES5 보다 개발자들이 효율적으로 코드를 작성 할 수 있도록

새로운 문법과 기능을 도입하였다.

 

그렇다고 JavaScript 버전이 2015년 업데이트 이후로 끝난것은 아니고,

아래와 같이 지속적인 업데이트가 유지되고 있다.

 

ECMAScript의 역사 및 버전
  1. ES1: 1997년에 처음 표준화
  2. ES2: 1998년에 발표, 주로 편집상의 수정
  3. ES3: 1999년에 발표, 정규 표현식, try/catch 예외 처리 등의 기능이 추가
  4. ES4: 매우 큰 변경을 포함하였으나, 결국 공식적으로는 미 발표
  5. ES5: 2009년에 발표, "strict mode"와 JSON 지원, 배열 메소드 등의 기능이 추가
  6. ES6: 2015년에 발표된 대규모 업데이트, 클래스, 모듈, 화살표 함수, let/const, 프로미스, 템플릿 리터럴 등의 기능이 추가
  7. ES7: 2016년에 발표, 지수 연산자(**)와 Array.prototype.includes가 추가
  8. ES8: 2017년에 발표, async/await, Object.entries(), Object.values() 등의 기능이 추가
  9. ES9: 2018년에 발표, 비동기 이터레이션, Rest/Spread 프로퍼티, 정규 표현식 개선 등이 포함
  10. ES10: 2019년에 발표, Array.prototype.flat, Array.prototype.flatMap, Object.fromEntries 등이 추가
  11. ES11: 2020년에 발표, BigInt, 동적 import(), null 병합 연산자(??), 선택적 체이닝 연산자(?.) 등이 포함
  12. ES12: 2021년에 발표, 논리 할당 연산자(&&=, ||=, ??=), String.prototype.replaceAll(), Promise.any() 등이 추가
  13. ES13: 2022년에 발표, 정규표현식 d 플래그, Object.hasOwn, 클래스 필드 선언 등이 추가

 

 

1- 1 let, const

앞서 TIL1 변수 부분에서도 소개하였지만 기존 var을 대체해서 나온 변수 선언 키워드 이며

 

var name = "name1"
console.log(name) // name1

var name = "name2"
console.log(name) // name2

 

var는 위 예제와 같이 재할당, 재선언이 가능하지만

 

아래 예제처럼

let재할당은 가능하고 재선언이 불가능하며

const재할당, 재선언 모두 불가능하다.

 

// let 키워드의 예시
let value = "value1"
console.log(value) // value1

value = "value2" // 재할당 가능
console.log(value) // value2

let value = "value3" // 재선언 불가능, SyntaxError: Identifier 'value' has already been declared



// const 키워드의 예시
const value; // 초기값 없이 선언 불가능, SyntaxError: Missing initializer in const declaration
---
const value = "value1"
console.log(value) // value1

value = "value2" // 재할당 불가능, TypeError: Assignment to constant variable.

const value = "value2" // 재선언 불가능, SyntaxError: Identifier 'value' has already been declared

 

1- 2 화살표 함수 (Arrow Function)

화살표 함수는 function이나 return 키워드 없이 함수를 만드는 간결한 함수 정의 방식이며,

문법이 간결할 뿐만 아니라, 기존의 함수 표현식과는 다르게 'this'를 바인딩 한다.

('this'바인딩 부분은 차후 배운것을 정리하며 포스팅 하겠다.)

 

// ES5
function func() {
	return true
}

//ES6
const func = () => true
const func = () => {
	return true
}

() => {}
parm => {}
(parm1, parm2, ...parms) -> {}

// 익명 화살표 함수
() => {}

 

위 예제와 같이 ES5의 기본적인 함수의 형태를

ES6의 업데이트를 통해 생겨난 화살표 함수를 통해 함수 자체를 선언하게 끔 할 수 있으며

특정조건(함수 내용의 매개변수가 하나인 경우) 에는 괄호가 생략될 수 있지만

매개변수가 아예 없는 경우에는 괄호가 다시 필요하다는 것을 명심해야 한다.

 

추가적인 주의 사항으로는 객체{}의 메소드로(차후 한번에 정리할 예정.)

화살표 함수를 사용하는것은 권장되지 않는다고 하며 이유는 자체 'this'를 갖고 있지 않기 때문이다.

여기서 또  'this'의 개념을 거론하는데  'this'는 현재 단계에서는 몰라도 되는 개념으로 넘어가자..

(  'this' 개념을 지금 설명하면 머리만 아프고.. 흥미도 떨어진다..😃..)

 

 

1- 3 삼항 연산자 (ternary operator)

삼항연산자는 지속적으로 반복되어 소개되는데 조건문에 가까운 개념으로

불리언 형식의 추론에 쓰이게 되고 기본 예제는 아래와 같다.

condition ? expr1 : expr2

console.log(true ? "참" : "거짓") // 참
console.log(false ? "참" : "거짓") // 거짓

 

앞서 TIL1과 TIL2를 통해 삼항 연산자를 잘 이해하면 if 문도 잘 이해하게 될 것이라 했는데,

개념은 둘다 조건문에 따라 다른 코드를 실행 할 수 있게 해주는 제어 구조 이지만

 

둘은 사용되는 상황과 목적이 조금 다르니 이점을 주의 해야 한다.

짧게 특징 비교만 해보자면 아래와 같다.

삼항 연산자 (Ternary Operator)

if 문 (if statement)

장점

  • 간결함: 짧고 간단한 조건부 할당이나 표현식을 작성할 때 매우 유용합니다.
  • 가독성: 간단한 조건식의 경우 코드가 짧아져 가독성이 높아집니다.

단점

  • 복잡한 로직에 부적합: 중첩되거나 복잡한 조건문을 삼항 연산자로 작성하면 가독성이 떨어지고 이해하기 어려워질 수 있습니다.

장점

  • 유연성: 복잡한 조건문과 여러 조건을 다루기에 적합합니다.
  • 명확성: 조건이 명확하게 구분되므로 가독성이 높습니다.

단점

  • 장황함: 단순한 조건문에 사용하면 코드가 불필요하게 길어질 수 있습니다.

 

 

1- 4 구조 분해 할당 (Destructuring)

지금까지 아는것만 나와서 지겨웠을 독자들을 위해 새로운것도 소개한다.

구조분해할당은 배열이나 객체의 구조를 분해하여 해당하는 값을 개별 변수에 쉽게 할당 할 수 있는 방법인데,

설명을 하면서도 꽤 복잡하게 느껴진다.

 

구조분해할당을 이해하면 오히려 코드를 간결하고 이해하기 쉽게 만든다고 하니..

무엇이든.. 방법만 알면 쉬워지게 되니.. 잘 따라와주길 바라며..

 

조금더 쉽게 설명하자면,

배열[] 이나 객체{}의 속성을 분해해서 그 값을 변수에 담을 수 있게 하는 방법이다.

 

1) 배열 []

배열의 경우 아래과 같이 코드가 있다고 가정한다면..

let [value1, value2] = [1, "new"];
console.log(value1); // 1
console.log(value2); // "new"

let [value1, value2] 선언에 = [1, "new"] ; 와 같다는 표현으로 구성하여

console.log(value1) 에 해당하는 값은 숫자 1로 하겠다고 약속

console.log(value2) 에 해당하는 값은 문자열 "new"로 하겠다고 약속한 것이고

 

위 두가지를 콘솔출력해보면 설명과 같이 결과는 숫자 1 과 문자열 "new"가 나오게 된다.

let arr = ["value1", "value2", "value3"];
let [a,b,c] = arr;
console.log(a,b,c) // value1 value2 value3

// let [a,b,c] = arr; 은 아래와 동일!
// let a = arr[0];
// let b = arr[1];
// let c = arr[2];

 

조금더 응용해 보자면 위 예제 스니펫과 같은데,

위 코드의 뜻은 let arr = ["value1", " value2", " value3"] ; 라는

let 선언 아래에 배열 [a, b, c]는 위 arr 선언과 같다는 표현으로 구성하여

console.log로 출력해보면 지금까지의 설명과 같이 value1, value2, value3 과 같이 배열의 형식을 벗겨 버리고

안에 구성된 value 값만 나오게 된다는 것이다.

 

그렇다면 만약 구조분해 할당을 해주는 다음의 매개체가 추가적인 값을 할당하게 되면 어떻게 될까?

let arr = ["value1", "value2", "value3"];

let [a,b,c,d] = arr;
console.log(d) // undefined

let [a,b,c,d = 4] = arr
console.log(d) // 4

위 예제는 앞서 설명한 예제와 다르게 배열 [a, b, c] 가아닌 배열 [a, b, c, d]로 하나를 더 추가하게 되었다.

이런 상황에서는 구조분해할당을 해줘야 하는 매개체인 let arr = ["value1", "value2", "value3"]; 에는

4번째 값이 없기 때문에 console.log(d)를 출력하게 될때   d에 대한 값이 "undefined" 로 출력되게 된다는 것이다.

그리고 3번째 코드 구문에서는 let[a, b, c, d=4] = arr 로 d에대한 값을 숫자 4로 할당을 해줬기 때문에

  d에 대한 값이 숫자 "4" 로 출력되게 된다.

 

배열의 경우는 위 와같은 방식으로 구조 분해할당이 가능하다.

 

2) 객체 {}

객체의 경우는 어떻게 구조분해할당이 이루어질까?

// 객체의 경우
let user = {name: "nbc", age: 30};
let {name, age} = user;

// let name = user.name;
// let age = user.age;

console.log(name, age) // nbc 30

 

위 예제와 같이 let user = {name: "nbc", age: 30}; 라는 객체 선언에

let {name, age} = user; 라는 코드 구문과 같이 객체의 key 값이 name과  age를 선언해서

해당 객체 key 값이 user의 key 값과 같다는 표현을 작성한다면

주석과 같이 첫번째 코드의 각 key에 해당하는 값을 서로 가져가게 되는것이다.

 

그래서 아래와 같이

console.log(name, age)로 출력을 한다면 user 선언값인 nbc와 30이 출력되며

각각 console.log(name)와 console.log(age)으로 출력한다고 했을때

객체에 대한 구조 분해 할당이 완벽히 이루어 졌기 때문에 

console.log(name)은 nbc로, console.log(age)는 30으로 출력되는것을 확인 할 수 있게 된다.

 

 

강의를 들으며 부족한 개념은 GPT에게 해설을 요청하여 공부를 보충하고 있는데

중첩 배열 [[]]중첩객체{{}}에 대한 구조분해 할당도 가능하다고 한다..

 

해당 내용에 대해서는 차후.. JavaScript에 좀더 적응이 될때 올리는것을 고려해 보겠다..

아니.. 고려만 해보겠다.. 😃..

 

📌

구조분해 할당은 눈으로만 봐선 이해가 되지 않으니

꼭! VS 코드와 같은 프로그램에서 직접 출력 해보기를 바람.

 

 

 

1- 5 단축 속성명 (property shorthand)

단축 속성명은 객체간 속성명과(property) 변수 이름이 동일한 경우  더 간결하게 작성할 수 있는 방법이다.

조금더 쉽게 말하자면 객체의 keyvalue 값이 같다면 생략이 가능하다는 말이다.

 

let name = 'John';
let age = 30;

let person = {
  name: name,
  age: age
};

console.log(person); // { name: 'John', age: 30 }

일반적인 객체 구문일때는 위와 같은 형식으로 name과 age를 명시했었다면

 

단축 속성명을 적용하여 아래와 같이 조금더 간결하게 정리가 가능하다.

let name = 'John';
let age = 30;

let person = {
  name,
  age
};

console.log(person); // { name: 'John', age: 30 }

 

결국 첫번째 예제에서 { name: name, age: age}으로  표현하여 name과 age가 중복되기 때문에

이런경우 {name, age}와 같이 단축 할 수 있다는 것이다.

이렇게 key value 값이 같다면 생략이 가능하고,

두 값 모두 console.log(person); 으로 출력해 보면 { name: 'John', age: 30 }이라는 값을 확인 할 수 있다.

 

1- 6 전개 구문 (Spread operator)

전개 구문은 배열 [] 이나 객체 {} 를 개별요소로 분해하여 사용 할 수 있게 해주는 문법이며,

구조분해할당과 함께 많이 사용되는 문법중 하나이다.

배열 전개 구문을 적용할 경우 배열 복사, 배열 병합, 함수 인자 전당 등의 장점이 있으며

객체 전개 구문을 적용할 경우 객체 복사, 객체 병합, 특정 속성을 덮어쓰기에 장점이 있다.

그리고 이어서 소개할 나머지 매개변수(rest parameter)도 전개 구문과 함께 쓰인다.

 

우선 전개 구문의 경우 아래의 예제와 같이 적용 될 수 있는데

// 배열
let arr = [1,2,3];

let newArr = [...arr, 4];
console.log(newArr) // [1,2,3,4]

// 객체
let user = {name: "nbc", age: 30};
let user2 = {...user}

user2.name = "nbc2"

console.log(user.name) // nbc
console.log(user2.name) // nbc2

첫번째 배열 [] 의 경우 예제와 같이 숫자 4를 배열에 추가해야할때 push 메소드를 사용해도 되지만

let newArr  = [...arr, 4] ; 라는 추가 선언을 통해 아주 간결하게 arr 배열에 4를 추가할 수 있게 된다.

4뿐 아니라 let newArr  = [...arr, 4, 5, 6, 7, 8, 9] ; 까지 작성했다면 arr 배열에 이어서 4 ~ 9 까지를 작성하게 된다.

 

두번째 객체 {} 의 경우도 위 예제 처럼 전개구문을 적용할 수 있는데,

let user = {name: "nbc", age: 30}; 라고 선언된 객체에 대하여 let = user2 객체 선언에

전개구문을 적용하면서  user2.name = "nbc2" 라고 적용할 수 있게 되었으며

console.log(user.name) 과  console.log(user2.name)을 각각 출력했을때

"nbc" 와 "nbc2"가 출력되는 것을 확인 할 수 있다.

 

1- 7 나머지 매개변수(rest parameter)

나머지 매개변수는 앞서 소개한 전개구문을 이해했다면 습득하는데 어렵지 않다.

보통 전개구문과 함께 사용되며 함수의 매개변수에서 사용되어 전달된 인자의 나머지를

배열로 받을 수 있게 해주는 문법이다.

 

아래의 예제와 함께 조금 더 자세한 설명을 통해 알아보자.

function func (a, b, ...args) {
	console.log(...args)
}

func(1, 2, 3) // 3
func(1, 2, 3, 4, 5, 6, 7) // 3 4 5 6 7

 

나머지 매개변수를 이해하려면 간단한 구조를 짚고 넘어갈 필요가 있다.(어렵진 않으니 걱정 NO)

바로 정규매개변수를 알아야 하는데 위 예제에서의  정규 매개변수는 바로 a, b  다.

function func (a, b, ...args) 처음 시작하는 함수의 도입부에서 a, b가 할당이 되어있고

이후에 ...args(아규먼츠)가  나머지 매개변수 즉, 레스트 파라미터 로 붙게 된다.

 

그래서 func(1, 2, 3) 이라는 요구에서 3은 원래 없는 값이지만

a, b 라는 정규 매개변수 뒤에 ...args(아규먼츠)라는 나머지 매개변수를 적용하여

비로소 3이라는 숫자가 함께 출력되게 되는것이다.

그리고 func(1, 2, 3, 4, 5, 6, 7) 에 대한 출력 값도 3 ~ 7 까지의 숫자는

당연히 나머지 매개변수에 의해 출력될 수 있게 된것이다.

 

1- 8 템플릿 리터럴 (Template literals)

템플릿 리터럴은 문자열을 작성할때 보다 간결하고 가독성 있게 표현할 수 있도록 해준다.

기존의 JavaScript 기능에서 문자열은 " string "과 같이 따옴표 안에서,

그리고 싱글라인에서 작성되고 표기되었는데,

 

이제는 키보드 숫자 배열 왼쪽에 있는 ```(백틱) 을 사용하여

 ` string `  과 같이 문자열을 감싸고 그안에  ${}문법을 사용하여 표현식을 포함 할 수 있게 되었다.

그래서 ` string ${} `  와 같은 표현이 가능해졌고 

아래 예제와 같이 구분하여 코드로 설명이 가능하겠다.

 

// 일반 문자열
console.log('string');
console.log('string');

// String 객체 생성
console.log(new String('string'));

// 템플릿 리터럴을 사용한 멀티라인 문자열
console.log(`string text
string text line2`);

// 템플릿 리터럴과 변수 포함
let value = 'dynamic';
console.log(`string text ${value} text`);

 

 

위 예제를 통해 출려된 결과

 

위 사진과 같이 ```(백틱) 을 사용하면 문자열 보간, 표현식 포함, 멀티라인 문자열 등 지원하며

최근 실무에서도 자주 쓰이는 문법이라고 하니 머릿속에 저장할 필요가 있어 보인다.

 

 

 

2. 일급 객체로써의 함수

JavaScript 에서 함수는 일급 객체로 구분된다.

그래서 함수를 객체처럼 여러가지 방식으로 다룰수 있는데,

이는 함수가 다른 데이터 타입과 동일하게 취급된다는 의미로

함수를 변수에 할당 하거나, 함수를 다른 함수의 인자로 전달 할 수 있으며,

함수에서 반환 값으로 사용 할 수 있다는 것을 포함한다.

 

더 깊은 설명은 차후 함수와 호이스팅, 콜백 함수 등 심화 과정에서

함수의 성격에 대해서 더 많이 알게 될 것이다.

 

자! 그래서 일급객체로써의 함수에서 소개 할 함수의 5가지 경우 및 특징은 아래와 같다.

변수에 함수를 할당
함수를 인자로 다른 함수에 전달
함수를 반환
객체의 프로퍼티(속성)으로 함수를 할당
배열의 요소로 함수를 할당

 

2- 1 변수에 함수를 할당

함수는 변수에 할당 할 수 있다.

함수는 값으로 취급 되는 특징이 있기 때문에

다른 변수들과 마찬가지로 변수에 할당 할 수 있다.

그리고 변수로 할당 된 함수는 나중에 사용할 수 있다.

 

아래의 예제를 통해 알아보자

const sayHello = function() {
  console.log('Hello!');
};

sayHello(); // "Hello!" 출력

 

예제를 보면 const로 선언한 sayHello 는 함수를 할당하고 있다.

그래서 console.log("Hello") 라는 출력 구문과 함께 

sayHello() ; 라고 함수(선언)의 끝에 명시 하고 있기 때문에

"Hello"를 출력하는것인데

 

 


주의 할 점은 위의 사진 처럼

console.log(sayHello) ; 자체를 호출하는 경우에는

아래의 사진과 같이 sayHello 로 선언한 함수 자체를 불러오기 때문에

값 출력을 위한 호출 구문을 작성할때는 명확하게 작성했는지를 한번 더 확인할 필요가 있다.

 

 

 

2- 2 함수를 인자로 다른 함수에 전달

함수는 다른 함수에 인자로 전달 될 수 있다.

앞서 설명했듯 함수는 값으로 취급 되는 특징이 있기 때문에

다른 함수의 인자로도 전달 할 수 있는데,

이것을 함수를 응용한 개념인 콜백 함수 or 고차함수라고 부르게 된다.

(차후 배우게 되며 상세히 설명할 예정이며 우선은 아래의 설명으로 인지 정도만 해도 충분하다.)

콜백 함수
다른 함수의 인자로 전달되어 실행되는 함수


고차 함수
함수를 인자로 받거나 함수를 반환하는 함수

 

그래서 고차함수는 2- 3 함수를 반환 부분에서 간략히 다루고

여기에서는 콜백함수를 아래 예제와 같이 간략히 다뤄보겠다.

function callFunction(func) {
  func();
}

const sayHello = function() {
  console.log('Hello!');
};

callFunction(sayHello); // "Hello!" 출력

 

위 예제에서는 처음에 함수를 설명하면서 다룬 

const sayHello = function() { console.log('Hello!'); }; 함수가 아래에 위치해 있고

해당 함수는 단순히 "Hello"를 출력하는 함수 이다.

 

우리가 주목할 것은 그 위에 있는 function callFunction(func) { func(); } 함수인데

처음 함수를 보게 된 사람들은 해석하기 쉽지 않을 것이다.

 

왜냐하면 바인딩의 개념이 들어가기 때문인데

지금은 "아 바인딩이 되는거구나?" 라고 생각하고 계속 설명을 들어주길 바란다.

 

현재 위의 function callFunction(func) { func(); } 함수는 callFunction에 (func)라고 할당을 하여

전달된 함수 func() ;를 호출하게 되어있는데,

이때 아래 callFunction(sayHello) ; 를 통해 sayHello 함수를 호출하여

callFunction 함수가 호출하려는 것이 함수임을 명시하고 있다.

 

설명을 덧붙여 정리해 보자면

 

  • callFunction 함수: 명령을 전달하는 역할,  "전달받은 함수를 실행해라"라는 명령을 수행
  • sayHello 함수: 실제 작업을 수행하는 역할, "Hello!"라는 메시지를 출력하는 작업을 수행
  • 함수 호출 과정: callFunction이 sayHello를 전달받아 실행함으로써 sayHello의 작업을 수행

이런 형식으로 함수를 인자로 다른 함수에 전달 할 수 있다.

(정말 어렵다..😀)

 

2- 3 함수를 반환

함수는 다른 함수에서 반환될 수도 있다.

앞서 설명했듯 함수는 값으로 취급 되는 특징이 있기 때문에

다른 함수에서 반환 할 수 있는데,

 

앞서 언급한 고차 함수나 함수 팩토리, 클로저 를 작성하는데 사용될 수 있다.

(우선 넘어가도 좋은 설명..)

 

그래서 아래 예제와 같이 고차 함수의 형태로도 다른 함수에서 반환될 수 있다.

 

function createAdder(num) {
  return function(x) {
    return x + num;
  }
}

const addFive = createAdder(5);
console.log(addFive(10)); // 15 출력

 

위 코드에서는 creatAdder 라는 함수가 매개변수로 숫자 num을 받는 함수이며

이 함수는 또 다른 함수 function(x) { return x + num; }을 반환하게 작성되어있다.

 

이때 아래의 const 선언을 통해 addFive 는 createAdder() 함수를 호출하면서 숫자 5를 인자로 전달하여

addFive라는 함수로 생성되며 5를 전달해준 함수가 되기 때문에

createAdder(num)은 const addFive = createAdder(5);를 통해 num = 5가 되며,

 

createAdder() 함수가 반환 하는 익명함수인 x의 값은 

console.log(addFive(10)) ; 이라는 출력 구문을 통해 전달되었으므로

 

비로소  x + num 은 10 + 5가되는것이다. 그래서 결과값은 15가 된다.

2- 4 객체의 프로퍼티(속성)으로 함수를 할당

함수는 객체의 프로퍼티(속성)으로 할당 될 수 있으며

객체의 프로퍼티로 함수를 할당하면, 그 함수는 객체의 메서드로 불리게 된다.

객체의 프로퍼티로 함수를 할당하는 것은 객체 지향 프로그래밍 패러다임을 구현하는데 중요한 요소다.

 

아래 예제를 통해 조금 더 알아보자

const person = {
  name: 'John',
  sayHello: function() {
    console.log(`Hello, my name is ${this.name}`);
  }
};

person.sayHello(); // "Hello, my name is John" 출력

 

예제를 설명하기 전 {} 객체 내부에는 어떤것이 다 들어와도 된다. 그것이 함수여도 된다.
라는 사실을 인지하며 듣는 다면 왜 함수가 객체에 들어와 있는지 충분한 이해가 될것이다.

 

 

예제에서 person {} 객체는 name 과 sayHello라는 두개의 프로퍼티를 가지고 있고,

sayHello 프로퍼티는 함수로 정의되어 있으며, 이함수는 객체의 메서드로 동작된다.

 

이 메서드를 호출하면 'this' 키워드를 사용하여 객체의 다른 프로퍼티로 접근할 수 있는데

예제 코드에서는 다른프로퍼티는 즉 name에 접근 할수 있는것이고

sayHello(){ } 함수 안에 템플릿 리터럴( `` 백틱)을 활용하여

console.log( `Hello, my name is ${this.name}` 가 들어가있기 때문에

person.sayHello() ; 라고 호출했을때  sayHello 함수의 값이 출력되게 되는것이다.

 

즉 sayHello 함수가 호출하려는 name 값이 출력되게 되는것이다.

2- 5 배열의 요소로 함수를 할당

함수는 객체의 배열의 요소로 할당 될 수 있으며

이를 통해 배열의 각 요소가 함수가 되어

각 해당하는 요소를 호출함으로써 함수를 실행 할 수 있다.

 

아래 예제를 통해 조금 더 알아보자.

const myArray = [
  function(a, b) {
    return a + b;
  },
  function(a, b) {
    return a - b;
  }
];

console.log(myArray[0](5, 10)); // 15 출력
console.log(myArray[1](10, 5)); // 5 출력

 

예제에서 const로 선언된 myArray 배열 [] 은 각 인덱스가 두개의 함수로 구성되어있다.

[ function(a, b) { return a + b; }, function(a, b) { return a - b; } ]

 

초록색은 인덱스 0 빨간색은 인덱스 1을 차지하고 있는 셈이다.

 

인덱스 0 은 a와 b를 더하고 인덱스 1은 a와 b를 빼는것으로 값을 반환하고 있기 때문에

console.log(myArray[0](5, 10)); 와 console.log(myArray[1](10, 5));로 출력을 하게 되면

각 해당하는 숫자를 더하고 빼게 되기 때문에 각각 15와 5의 숫자를 출력하게 되는것이다.

 

 

3. Map과 Set

JavaScript에서 객체 {} 와 배열 []을 이용하면 굉장히 다양하고 복잡한 프로그래밍을 할 수 있다.

그럼에도 불구하고 여러가지 문제들을 프로그래밍 적으로 반영하기엔 부족한데,

해당 한계를 극복하고자 비교적 최근 등장한 자료구조 이며 각각 객체 {} 와 배열 [] 보다 

효율적으로 데이터를 처리 할 수 있는 기능을 제공한다.

 

3- 1 Map

Map 객체는 key - value pair를 저장하며, key - value 모두 어떤 타입도 가능하다.

Map은 객체와 달리 키가 반드시 문자열일 필요가 없고, 삽입 순서를 기억한다

그리고 맵에는 다음과 같은 주요 메서드와 프로퍼티가 있다.

  • new Map() – 맵 제작
  • map.set(key, value) – key를 이용해 value를 저장
  • map.get(key) – key에 해당하는 값을 반환 /  key가 존재하지 않으면 undefined를 반환
  • map.has(key) – key가 존재하면 true / 존재하지 않으면 false를 반환
  • map.delete(key) – key에 해당하는 값을 삭제
  • map.clear() – 맵 안의 모든 요소를 제거
  • map.size – 요소의 개수를 반환

 

 

새로운 Map을 만들려면 Map() 생성자를 사용

const myMap = new Map();

 

이제 Map에 값을 추가하려면 set() 메소드를 사용

myMap.set('key', 'value');

 

Map에서 값을 검색하려면 get() 메소드를 사용

console.log(myMap.get('key')); // 'value' 출력

 

추가적으로 Map에서는 반복도 실행할 수 있는데

이때 for ...of 반복문을 사용한다.

 

아래 예제를 통해 쉽게 설명 할 수 있는데

var iterable = [10, 20, 30];

for (var valueof iterable) {
  console.log(value);// 10, 20, 30
}

 

위 내용과 같이 var iterable = [10, 20, 30]; 라는 배열이 있을때

각 배열에 속해있는 인덱스 값을  for ...of 반복문을 통해 반복하여 

값을 출력할 수 있고, 순서를 간략히 설명하자면

for ...of 반복문을 통해 value는 iterable 배열의 첫번째 요소 인 10을 먼저 출력하고

그다음에 두번째 요소인 20을 출력 끝으로 세번재 요소인 30을 출력하는 형태로

모든 값을 출력해준다.

 

 

const myMap = new Map();
myMap.set('one', 1);
myMap.set('two', 2);
myMap.set('three', 3);

for (const key of myMap.keys()) {
  console.log(key);
}

for (const value of myMap.values()) {
  console.log(value);
}

for (const entry of myMap.entries()) {
  console.log(`${entry[0]}: ${entry[1]}`);
}

 

Map의 크기를 확인하려면 size 속성을 사용

console.log(myMap.size); // 3 출력


특정 키가 Map에 존재하는지 여부를 확인하려면 has() 메소드를 사용

console.log(myMap.has('two')); // true 출력

3- 2 Set

set 객체는 유일한 값들의 컬렉션 이다.

중복된 값은 허용되지 않으며, 삽입 순서를 기억한다.

 

Set으로 할수 있는 작업들

  • 값 추가 및 검색
  • 값 삭제
  • 모든 값 제거
  • Set 크기 및 존재 여부 확인

 

새로운 Set을 만들려면 Set() 생성자를 사용

const mySet = new Set();

 

이제 Set에 값을 추가하려면 add() 메소드를 사용

mySet.add('value1');
mySet.add('value2');

 

Set에서는 values() 메소드를 사용하여 값을 반복할 수 있다.

const mySet = new Set();
mySet.add('value1');
mySet.add('value2');
mySet.add('value3');

for (const value of mySet.values()) {
  console.log(value);
}

 

 

Set의 크기를 확인하려면 size 속성을 사용

console.log(mySet.size); // 3 출력

 

 

특정 값을 Set에서 검색하여 존재하는지 여부를 확인하려면 has() 메소드를 사용

console.log(mySet.has('value2')); // true 출력

 

 

728x90
반응형

댓글