복잡한뇌구조마냥

JavaScript 개념 알고 가기 본문

이노베이션 캠프

JavaScript 개념 알고 가기

지금해냥 2022. 8. 6. 13:56

1. JavaScript의 자료형과 JavaScript만의 특성은 무엇일까?

1) 느슨한 타입(loosely typed)의 동적(dynamic) 언어

  - 자바스크립트는 느슨한 타입의 동적 언어로 변수가 자료형에 관계 없이 데이터가 입력이 가능하다.

  - 변수를 선언할 때 자료형에 따라 int, string 등이 아닌 var, let, const 등으로 선언해 해당 값에 따라 입력이 가능하다. 

 

    JavaScript의 자료형은 다음과 같다

  - 숫자형 : 숫자를 담을 수 있는 자료형이다. ex) 10, 1, 2, 3

  - BigInt : 자바스크립트의 일반 자료형의 길이가 정해져 있어 그 이상의 큰 수를 담을 때 사용하며, 끝에 n이 붙는다.

  - 문자형 : 문자를 담을 수 있는 자료형이다. ex) "Hello New World", "10", "1", "abc"

  - Boolean형 : 참, 거짓을 판별할 수 있는 값을 할당하는 자료형이다. ex) True, False

  - null : 해당 위치에 값이 비어있다는 것을 표현한다. (아무것도 들어 있지않은 형태)

   -undefined : 변수라던지 값이 할당이 되어있지 않은 값을 표현하는 자료형이다.

   -typeof : 해당 값의 자료형이 무엇인지 나타내는 자료형이다. ex) "10" : String, 10:int, True: Boolean, 131314142n: BigInt

   -object: 오브젝트는 Symbol값으로 배열과 같이 주소값을 참조하여 사용하는 자료형이다.

 

2) JavaScript 형변환

 - 자바 스크립트의 형변한은 자료형 선언이 없음에 따라 자유롭게 가능하다.

 - 숫자 값을 toString 함수를 통해서 문자열로 바꾸거나,

 - 문자형태의 숫자를 Number을 통해서 바꾸고

 - Boolean으로 true, false를 구할 수도 있다.

- String으로의 형변환은 글자로 변형하게 때문에 유연하게 가능하나,

   Number과 같은 경우 글자를 숫자로 변경할 수 없기 때문에 유의가 필요하다.

String(12345)                   // "12345"
String(-3.14)                   // "-3.14"
String(true)                    // "true"
String(false)                   // "false"
String(undefined)               // "undefined"
String(null)                    // "null"
String(BigInt(42))              // "42"

 

3) =,==, ===

 - 언어를 사용할 때 = 로 선언해주는 것은 해당 변수에 값을 넣을 때에다.

 - ==의 경우 =과는 완전히 다른 기능이다. 보편적으로 수학에서 같다와 표현하는 방식이라고 생각하면 쉽다.

 - 해당 값의 값이 같은지 다른지의 결과를 출력 할 수 있다.

 - ===의 경우는 ==와는 조금 다르다. ==의 경우 해당 값을 비교하지만, ==은 자료형을 비교한다. 

2 == "2" // expected output: true
2 === "2" // expected output: false 


4) 느슨한 타입(loosely typed)의 동적(dynamic) 언어의 문제점은 무엇이고 보완할 수 있는 방법에는 무엇이 있을지 생각해보세요.

 - 자료형 변환이 자유롭기 때문에 입력에 따라 원하는 값과 다른 입력 시에도 들어가기 때문에 입력에 유의하여야 한다.

 실수가 많이 일어날 수 있는 문자형과 숫자형의 경우 var과 let등으로 구분하는 등 본인만의 규칙을 만드는 방법도 있다.

 

5) undefined와 null의 미세한 차이들을 비교해보세요.

null == undefined // expected output: true
null == undefined // expected output: false 
console.log(typeof null);	// expected output: "object"
console.log(typeof undefined);  // expected output: "undefined"

- null의 typeof는 object로 나오지만 이것은 언어의 오류일 뿐 null은 독립적인 자료형을 갖는다.

- 둘 다 내용이 비어있다는 것은 같다고 볼 수 있으나, null은 존재자체가 없다는 의미이고,

  undefined는 존재는 규정되어 있으나 값이 할당되지 않았다고 봐야한다. 차이를 알고 개념과 용도를 명확히 구분하자.
 


2 JavaScript 객체와 불변성이란 ?

1) 기본형 데이터와 참조형 데이터

  기본형

 - 기본형 데이터는 변하지 않는 원시타입의 데이터를 의미한다.

 - 위의 자료형에서 Object를 제외한 숫자형, 문자형, BigInt, Boolean, null, undefined, typeof을 의미한다.

 - 할당하는 내용은 변해도 값 자체는 변하지 않는다.

   참조형

  - 참조형은 Object처럼 만들어진 곳의 주소를 참조하여 내용을 사용하는 방식이다.

  - 배열의 경우 array[0]의 경우 배열이라는 고정된 값이 아닌 array의 주소를 불러와 0번째 값을 사용하는 것이다.

 

 2) JavaScript 형변환

   - 자바스크립트는 참조형 데이터를 사용한다.

var A = "Hllo New World"
var B= A;
B = "I`m Big World"

   - 위와 같은 구문이 있다고 가정하면, B는 A라는 값을 받아와 B가 가지고 있는 주소값에 할당하는 것이다.

     A,B는 각각의 독립적인 주소를 가지고 값을 할당하여 보여주는 방식을 사용한다.

 3) 불변 객체를 만드는 방법

   불변 객체를 만드는 방법은 Object.freeze()를 사용하여 만들 수 있다.

 

- 위의 코드를 보면 Object.freeze를 통해 user1 을  불변 객체로 만들었기 때문에 name을 변경하려고 해도 바뀌지않는다.

  허나 Object내 내부 객체는 변경이 가능하다. 내부 객체까지 불변 객체로 사용하려면 Deep freeze를 하여야 한다.

 

 4) 얕은 복사와 깊은 복사

    얕은 복사

     - 얕은 복사는 객체를 복사할 때 밑의 예제처럼 원래값과 복사된 값이 같은 참조를 가리키고 있는 것을 말한다. 객체안에 객체가 있을 경우 한개의 객체라도 원본 객체를 참조하고 있다면 이를 얕은 복사라고 한다.

얕은 복사는 원본과의 연결점이 유지되어 독립적인 객체라고 보기 어렵기 때문에

복사가 덜된거같다은 생각든다. 느낌이 다르다.

const a = {number: 1};
let b = a;

b.number = 2

console.log(a); // {number: 2}
console.log(b); // {number: 2}

    깊은 복사

    -깊은 복사는 복사된 개체는 객체안에 객체가 있을 경우에도 원본과의 참조가 완전히 끊어진 객체를 말한다.

     따라서 원본과 사본은 각각 독립적인 객체로서 역할을 하게된다. 완전 분리된 복사 깊은 복사이다.

    


3. 호이스팅과 TDZ는 무엇일까 ?

1) 스코프, 호이스팅, TDZ

   스코프(Scope)란?

    - 직접적인 번역으로는 '범위'라는 뜻을 가진다. 자바스크립트에서 스코프는 2가지 타입이 있다.

    - Global(전역 스코프) - 문서 전체에 할당하는 값을 지니는 범위이다.

    - Local(지역 스코프) - 만약 함수가 있다면 함수 내에서만 적용 가능한 범위이다.

 

   호이스팅(Hoisting)이란?

    - 호이스팅은 변수와 함수의 메모리 공간을 선언 전에 미리 할당하는 것을 의미한다.

    - 함수를 사용한다고 하면 해당 함수가 무엇인지 문서에게 알려주는 것이 호이스팅이다.

    - 따라서 함수는 우선순위가 밑에 작성하여도 우선되어 타 변수나 객체보다 먼저 할당된다.

function catName(name) {
  console.log("제 고양이의 이름은 " + name + "입니다");
}

catName("호랑이");

   해당 코드는 catName이라는 함수를 사용하기전에 catName을 미리 선언해주었다.

catName("클로이");

function catName(name) {
  console.log("제 고양이의 이름은 " + name + "입니다");
}

   허나 해당 코드는 catName을 선언하기 전에 함수를 먼저 사용하였다.

   두 경우의 결과에서 아래쪽 코드는 오류가 나는가? 아니다. 호이스팅때문이다.

   함수의 경우 밑에 작성하여도 호이스팅에 의해 우선순위가 변경된다. 함수가 위에서 먼저 처리되는 것이다.

 

   TDZ(Temporal Dead Zone)란?

 - 직역하면 시각적 사각지대라는 뜻으로,  예를들어 선언 되지않은 변수를 사용하는 공간을 얘기한다.

 - 선언이 되지않아서 사용하지 못하는 공간이다. 위치로 보면 변수 선언의 윗부분에 해당한다고 본다.

 - 따라서 TDZ에는 변수를 작성해도 작동이 되지않는다. 그러므로 해당 변수를 사용하면 안되는 공간이다.

 

2) 함수 선언문과 함수 표현식에서 호이스팅 방식의 차이

   함수 선언문과 함수 표현식의 차이를 보기전에 선언문과 표현식의 차이를 보고가자.

var B;

B = "I`m Big World"

  - 위에서 사용한 코드는 첫째 줄은 선언문이다.

  - 밑에 줄은 표현문이다.

  - 해당 코드는 호이스팅의 영향을 받지않지만, 선언문이 있기 전에 표현문이 있으면 동작하지않는다.

function B = function (a, b){
    return a+b;
}

function A(a,b) {
    return a+b;
}

  - 해당 구문은 대충 함수의 표현문과 선언문이다. 같은 함수이지만 호이스팅 대상으로서는 다르다.

  - 해당의 경우 function A는 호이스팅의 영향을 받아 문서 위쪽으로 넘어가서 우선으로 적용된다.

  - 허나 function B는 변수처럼 해당 위치에서 적용될 뿐 호이스팅의 대상이 되지않는다.

  - 따라서 호이스팅은 선언문에서는 적용되어 우선순위가 변하지만 표현문은 호이스팅의 대상이 아니다.

 

3) 여러분이 많이 작성해온 let, const, var, function 이 어떤 원리로 실행되는지 알 수 있어요.

function B{
    var a = 10;
    let b = 5;
    const c = 6;

    return a+b+c;
}
a = 5; // Error
b = 10; //success
c = 10; //success

  - var : 호이스팅이 되지않는다. 함수내(지역)에서 선언되었을 경우 함수내에서만 사용이 가능하다.

             문서전체(전역)에서 사용하려면 변수의 재 선언이 필요하다.

  - let, const : 호이스팅이 적용된다. 따라서 함수내에서 선언되어도 지역변수를 전역변수처럼 선언이 가능하다.

  - function : 선언문 표현시 호이스팅으로 우선적으로 적용된다.

    

4) 실행 컨텍스트와 콜 스택

     실행 컨텍스트 :  실행 컨텍스트는 실행할 코드에 제공할 환경 정보들을 모아놓은 객체입니다. 

                                쉽게 얘기하면 함수가 동작할 때 함수 내부의 우선순위를 정해서 나온 순서도라고 보면 됩니다.

                                호이스팅도 실행 컨텍스트를 구성을 위한 동작이라 볼 수 있습니다.

catName("클로이");

function catName(name) {
  console.log("제 고양이의 이름은 " + name + "입니다");
}

 해당 코드를 예로 보겠습니다.

function catName(name) {
  console.log("제 고양이의 이름은 " + name + "입니다");
}
catName("클로이");

 - 전체 실행 컨텍스트는 호이스팅으로 함수가 먼저 선언되고 동작하는 것으로 바뀔 것이고,

var name = "클로이"
"제 고양이의 이름은 " + name + "입니다"  -> "제 고양이의 이름은 클로이 입니다"
console.log("제 고양이의 이름은 클로이 입니다");

 - 함수 내부동작은 name값을 함수 사용에서 받아 로그 속 내용을 합쳐주고 그 뒤에 출력을 할 것입니다.

 - 이처럼 순서를 나열하여 동작하는 것이 실행 컨텍스트라고 볼 수 있습니다. 

    콜 스택 : 콜 스택은 자바스크립트 코드가 실행되며 생성되는 실행 컨텍스트를 저장하는 자료구조라고 볼 수 있습니다.

                   스택에 대해 먼저 알아봅시다.

 스택은 쉽게 항아리에 물건을 밑에서 부터 차곡차곡 채우는 자료구조 입니다.

콜스택도 실행과정을 전체 문서가 동작할 수 있게 실행 컨텍스트를 스택에 쌓아놓는다고 생각하면 됩니다.

 

  - 전체 과정을 보면 문서는 전역변수부터 스택에 쌓다가 함수가 선언되면 함수내용부터 쌓아서 해결하고 꺼내주고

    그 뒤에 함수 아래쪽으로 내려가 다음 문서내용을 처리하는 것입니다.

 

5) 스코프 체인, 변수 은닉화

- 스코프 체인 : 스코프 체인은 현재 자신의 scope에서 사용하고자 하는 변수가 없다면 Scope Chain을 통해 찾게됩니다.

                        ex) 함수내에 지역변수가 없다면 전역변수를 찾는 것

 -변수 은닉화 : 변수 은닉화는 말 그래도 변수를 외부에서 사용할 수 없게끔 숨기는 것이라고 보면됩니다.

                       타 언어의 private같은 방식이 자바스크립트에는 없기 때문에

                       자바스크립트에서 변수은닉을 위해서는 함수를 사용해야합니다.

function a(){
  let temp = 'a' 
  
  return temp;
} 

// console.log(temp)  error: temp is not defined
const result = a()
console.log(result); //a

 간단한 예제로 다음과 같이 선언하면 temp를 외부에서 바로 출력못하게 막는겁니다.

 이는 자바스크립트에서 객체지향적 프로그래밍을 하기위한 수단으로 쓰이고 있습니다.

function hello(name) {
  let _name = name;
  return function () {
    console.log('Hello, ' + _name);
  };
}

let a = new hello('영서');
let b = new hello('아름');

a() //Hello, 영서
b() //Hello, 아름

살짝 심화 과정으로 다음과 같은 예를 가져왔습니다.

name을 사용하기위해서는 hello라는 함수를 통해서 객체를 사용해야지만 함수 내부적으로 접근하여 사용가능합니다.

자바스크립트는 자료형이 자유롭고 느슨한 언어의 동적언어이기 때문에

class가 아닌 함수를 통해서 객체를 사용할 수 있습니다. 


실습 과제

1) 콘솔에 찍힐 b 값을 예상해보고, 어디에서 선언된 “b”가 몇번째 라인에서 호출한 console.log에 찍혔는지,

왜 그런지 설명해보세요. 주석을 풀어보고 오류가 난다면 왜 오류가 나는 지 설명하고 오류를 수정해보세요.

let b = 1;
//let a = 0; // 방법 2
function hi () {
    const a = 1;
    let b = 100;
    b++;

    console.log(a,b);

    //console.log(a); // 방법 1

}
//console.log(a); //에러발생 원인
console.log(b);

hi();

console.log(b);


 - 해당 코드의 주석 제거 시 에러 발생요인은 console.log(a)의 a가 선언 되지 않았기 때문에다.

  - 함수 내 const a는 함수 내에서 기능하는 변수로 함수 외부의 호출에 반응하지 못한다.

  - 따라서 이 문제의 해결방법은 console.log(a)를 함수 내부로 보내는 방법이 있다.

    추가적으로 2번째 방법으로는 console.log(a)의 변수 a를 함수 위에서 선언해주는 것이다.

    그러면 함수내 a와는 별개로 a값의 로그를 호출 할 수 있다.

 

그림 참조 출처 : https://velog.io/@howooke/JavaScript%EC%9D%98-%ED%8A%B9%EC%84%B1

 

JavaScript의 특성

느슨한 타입(loosely typed)의 동적(dynamic) 언어 JavaScript는 느슨한 타입(loosely typed)의 동적(dynamic) 언어입니다. JavaScript의 변수는 어떤 특정 타입과 연결되지 않으며, 모든 타입의 값으로 할당 (및 재

velog.io

                          https://poiemaweb.com/js-immutability

 

Immutability | PoiemaWeb

함수형 프로그래밍의 핵심 원리이다. 객체는 참조(reference) 형태로 전달하고 전달 받는다. 객체가 참조를 통해 공유되어 있다면 그 상태가 언제든지 변경될 수 있기 때문에 문제가 될 가능성도

poiemaweb.com

https://developer.mozilla.org/ko/docs/Glossary/Hoisting

 

호이스팅 - 용어 사전 | MDN

JavaScript에서 호이스팅(hoisting)이란, 인터프리터가 변수와 함수의 메모리 공간을 선언 전에 미리 할당하는 것을 의미합니다. var로 선언한 변수의 경우 호이스팅 시 undefined로 변수를 초기화합니다

developer.mozilla.org

https://frontj.com/entry/8-Javascript%EC%9D%98-%EC%BD%9C-%EC%8A%A4%ED%83%9D%EA%B3%BC-%EC%9D%B4%EB%B2%A4%ED%8A%B8-%EB%A3%A8%ED%94%84

 

8. Javascript의 콜 스택과 이벤트 루프

지난 포스트에서 잠깐 다루었던 콜 스택(call stack)에 대해 알아보고, 조금 더 나아가 자바스크립트는 한 순간 하나의 작업만 처리할 수 있는 단일 스레드 기반의 언어임에도 불구하고 동시에 많

frontj.com

https://velog.io/@0seo8/JS-%EC%9D%80%EB%8B%89%ED%99%94-os17ra37

 

[Javascript] 은닉화

클로저의 은닉화 1. Intro 자바스크립트의 함수를 활용을 하면, 함수를 통해서 어느정도 은닉화를 할 수 있다고 해 IIFE(즉시실행함수호출)을 활용한 적이 있습니다. 함수 외부에서 a를 출력해보면

velog.io

 

LIST