Javascript없이 HTML 과 CSS 로는 단순히 정적인 페이지를 보여주는것만 가능하다.

(CSS 옵션 및 애니메이션이 아닌 데이터의 요청 등의 '변화' 를 기준으로 정적임을 판단.)

 

만약 새로고침 없이 동적으로 데이터를 받아오고 싶다면 Javascript로 서버에 통신을 요청하면 된다.

 

이런 방법을 어디에 사용할 수 있을까??

사실 현대 웹 에서는 UX의 모든곳에 사용하고 있다.

 

Chrome 브라우저의 개발자도구 > 네트워크 탭으로 확인해보자.

 

네이버 모바일 페이지의 홈 화면이다.
뉴스 탭을 클릭할때 데이터들이 받아지는것을 볼 수 있다.

 

이 데이터들의 통신을 AJAX 통신이라고 한다. (Asynchronous JavaScript And XML)

Asynchronous (비동기) 임에 주의하자.

 

Ajax 통신을 간단히 말하면 "서버와 통신하기 위해 XMLHttpRequest 객체를 사용하는 것" 이다.

 

Javascript는 브라우저에서 Ajax 통신을 지원하기 위해 자연스럽게 비동기를 지원하게 되었고,

브라우저의 자바스크립트 엔진은 싱글 스레드 기반이므로, 하나의 스레드로 이를 처리해야만 했다.

 

이 글에서는 Ajax 통신과 비동기에 대해서 설명한다.

 

 

Ajax 시작하기

본 문서는 AJAX의 기본을 익힐수 있도록 해주며, 두 가지 간단한 훈련용 예제를 제공합니다.

developer.mozilla.org


Ajax (Asynchronous JavaScript And XML)

소개글에서 웹 페이지에서 Ajax 통신을 어떻게 사용하는 지를 설명했다.

 

만약, 첫 메인페이지에서 다른 탭들의 데이터를 한꺼번에 로딩한다면 비동기 통신을 할 필요가 없다.

 

다만 이 경우 초기 브라우저 로딩 속도가 매우 느려지며, 사용자가 사용하지 않을 가능성이 있는 정보까지 요청한다.

거기다 사용자가 많아질 경우 서버에 큰 부담이 된다.

 

Ajax 통신으로 JSON, XML, HTML 그리고 일반 텍스트 형식 등을 포함한 다양한 포맷을 주고받을 수 있다.

그 중에서 일반적으로 사용이 편한 JSON 형식을 주고받는 방법을 사용한다.

JSON 

 

JSON (JavaScript Object Notation)은 경량의 DATA-교환 형식이며, 

Javascript에서 객체를 만들 때 사용하는 표현식 이다.

 

이 형식은 사람이 읽고 쓰기에 용이하며, 기계가 분석하고 생성함에도 용이하다.

 

특정 언어에 종속되지 않는다는 특징이 있다.

따라서 대부분의 프로그래밍 언어에서 JSON 포맷의 데이터를 핸들링 할 수 있는 라이브러리를 제공한다.

 

우선 JSON 데이터를 확인해보자

 

{
  "squadName": "Super hero squad",
  "homeTown": "Metro City",
  "formed": 2016,
  "secretBase": "Super tower",
  "active": true,
  "members": [
    {
      "name": "Molecule Man",
      "age": 29,
      "secretIdentity": "Dan Jukes",
      "powers": [
        "Radiation resistance",
        "Turning tiny",
        "Radiation blast"
      ]
    },
    {
      "name": "Madame Uppercut",
      "age": 39,
      "secretIdentity": "Jane Wilson",
      "powers": [
        "Million tonne punch",
        "Damage resistance",
        "Superhuman reflexes"
      ]
    }
  ]
}

JSON 데이터는 Key 와 Value로 이루어진 쌍의 데이터들을 가진다. : { String key : String value }

Key는 유일해야하며, Value로는 일반 값과 배열, JSON을 포함한 값들을 가진다.

 

JSON 내부에 JSON데이터를 넣을 수 있으므로 위 예시와 같이 응용할 수 있다.

 

JSON을 다룰 때 자주 사용하는 메소드로는 다음 두가지가 있다.

  • JSON.parse(JSON으로 변환할 문자열) : JSON 형식의 텍스트를 자바스크립트 객체로 변환한다.
  • JSON.stringify(JSON 문자열로 변환할 값) : 자바스크립트 객체를 JSON 텍스트로 변환한다.

다음 예제를 실행해보자

var jsonText = '{ "key": "value" }';
var realObject = JSON.parse(jsonText);

realObject	// {key: "value"}

var realObjectTojsonText = JSON.stringify(realObject);

realObjectTojsonText // "{"key":"value"}"

형식이 맞을경우 문자열을 JSON 데이터로 변환할 수 있다.

 

Ajax를 실행해보자

function ajax() {
 var oReq = new XMLHttpRequest();
 
 oReq.addEventListener("load", function() {
   console.log(this.responseText);
 });    
 
 // 요청방식, url, 비동기적으로 실행될지 boolean (생략가능)
 oReq.open("GET", "https://hacker-news.firebaseio.com/v0/topstories.json");
 oReq.send();
}

// 위 함수를 실행시켜보자
ajax()

출처 : 부스트코스 강의 내용 중

 

oReq는 XMXMLHttpRequest 로 생성된 객체이다.

 

이 객체에 이벤트 리스너로 load 되었을 때 console로 responseText를 출력하도록 설정했다.

여기서 this 바인딩을 사용했는데, 이 this는 함수의 인자로 자동으로 전달되는 객체를 가리킨다.

 

this 바인딩이 어려울 경우 다음 코드로 이해해도 된다.

function reqListener (e) {
    console.log(e.responseText);
}

 oReq.addEventListener("load", reqListener);  

 

open 메소드를 통해 요청방식, 주소, 비동기 여부를 지정하고,

send 메소드를 이용해 보낸다.

 

 

ajax함수를 실행시킨 경우 무언가 데이터가 출력되는것을 확인할 수 있다.

 

비동기

여기서 데이터의 출력이 '조금 늦게' 일어나는것을 유심히 살펴보자.

Chrome 개발자도구의 네트워크 탭을 열고 확인해보자

 

ajax()를 실행시키고 나서 데이터를 요청 후 받아오는데 171ms가 걸렸다.

요청처리가 완료되면(서버에서 응답이 오면) load이벤트가 발생하고, 콜백함수가 실행된다.

이 콜백 함수는 console.log를 실행하는 함수이다.


콜백함수가 실행될 때, ajax함수는 이미 콜스택에서 사라진 상태이다.

즉 ajax함수에서 oReq.send 가 끝날때까지 기다리지 않고, 서버에 요청만 보낸 뒤 ajax함수는 끝난것이다.

이는 setTimeout함수의 콜백함수의 실행과 유사하게 동작하는 '비동기'로직 이다.

 

자바스크립트는 싱글스레드이므로, 중간 중간 서버에 데이터를 요청하거나 setTimeout등과 같은 비동기 처리를 구현하기 위해 다음과 같은 구조를 사용한다.

 

자바스크립트 엔진, 이벤트 큐, WEb API

다음 동영상을 보면 더 자세한 설명이 나와있다.

 

 

Ajax의 응답 처리

서버로부터 받아온 JSON 데이터는 문자열 형태이다.

이는 문자열이므로 Javascript에서 사용하기 위해 문자열을 JSON으로 변화시켜주어야한다.

 

이때 JSON.parse 메소드를 사용한다.

var json객체로변환된값 = JSON.parse("서버에서 받은 JSON 문자열");

Ajax의 단점

동적인 웹과, 필요한 데이터만 전송할 수 있는 방식인 Ajax에는 다음과 같은 단점이 존재한다.

  • 히스토리 관리가 되지 않는다. (브라우저의 뒤로가기 앞으로가기 등과 상관 없는 데이터 전송) 
  • 연속으로 데이터를 요청하면 서버 부하가 증가할 수 있다.
  • XMLHttpRequest를 통해 통신을 하는 경우사용자에게 아무런 진행 정보가 주어지지 않는다.
  • 그래서 아직 요청이 완료되지 않았는데 사용자가 페이지를 떠나거나 오작동할 우려가 발생하게 된다. 

진행정보가 주어지지 않아 사용자가 로딩 중에 이탈하는 경우가 발생할 수 있음에 유의하자!

 

히스토리는 History객체를 의미한다. 자세한 내용은 아래 링크에서 확인하자.

 

History

History 인터페이스는 브라우저의 세션 기록, 즉 현재 페이지를 불러온 탭 또는 프레임의 방문 기록을 조작할 수 있는 방법을 제공합니다.

developer.mozilla.org

 


AJAX의 경우 비동기 방식이므로, Javascript의 매우 중요한 성질 중 하나를 사용하고 있다.

 

처리 과정을 파악하고 있다면, 앞으로 마주할 비동기 문제에 좀더 유연하게 대처할 수 있을것이다.

 

 

[LECTURE] 4) Ajax통신의 이해 : edwith

들어가기 전에 브라우저의 새로고침 없이 데이터를 얻어오는 방법이 있습니다. 이는 사용자가 더 빠르게 변경된 데이터를 화면의 새로고침 없이 확인할 수 있는 방법으로 더 좋은 UX(U... - 부스트코스

www.edwith.org

 

 

[LECTURE] 1) Ajax 응답 처리와 비동기 : edwith

들어가기 전에 브라우저의 새로고침 없이 데이터를 얻어오는 방법이 있습니다. 더 좋은 UX(User Experience)를 제공하는 좋은 방법이니, 알아보도록 하죠.     학습 목... - 부스트코스

www.edwith.org

 

우리가 무언가를 클릭하거나, 현재 보고있는 창을 새로고침할 때, 창을 닫을 때 등등

브라우저에서 일어나는 동작에 대해서 Event가 발생한다.

 

즉 브라우저는 Event 기반으로 동작한다고 할 수 있다.

 

이러한 다양한 종류의 Event에 대해서 알아보자

 

https://www.edwith.org/boostcourse-web/lecture/16700/

 

[LECTURE] 3) Browser Event, Event object, Event handler : edwith

들어가기 전에 어떤 영역을 마우스 클릭하거나, 화면을 스크롤 하거나 하는 작업에 따라서 브라우저는 반응합니다. 이런 것들은 모두 브라우저가 Event기반으로 동작되게 만들어졌기 때... - 부스트코스

www.edwith.org


Event객체

브라우저에서 발생하는 모든 동작에 대해서 이벤트가 발생한다.

  • 클릭
  • 브라우저의 화면의 크기를 마우스로 조정
  • 마우스 휠로 스크롤
  • 마우스로 어떤 것을 이동

모든 DOM 노드는 이런 신호를 만들어 낸다. 하지만 이벤트는 DOM에만 한정되진 않는다.

 

https://ko.javascript.info/introduction-browser-events

 

브라우저 이벤트 소개

 

ko.javascript.info

 

자주 사용되는 이벤트는 다음과 같다.

 

마우스 이벤트

  • click : 요소 위에서 마우스 왼쪽 버튼을 눌렀을 때
  • contextmenu : 요소 위에서 마우스 오른쪽 버튼을 눌렀을 때
  • mouseover, mouseout : 마우스 커서를 요소 위로 움직였을 때, 커서가 요소 밖으로 움직였을 때
  • mousedown, mouseup : 요소 위에서 마우스 왼쪽 버튼을 누르고 있을 때, 마우스 버튼을 뗄 때
  • mousemove : 마우스를 움직일 때

폼 요소 이벤트:

  • submit : 사용자가 <form>을 제출할 때
  • focus : 사용자가 <input>과 같은 요소에 포커스 할 때

키보드 이벤트

  • keydown과 keyup : 사용자가 키보드 버튼을 누르거나 뗄 때

문서 이벤트

  • DOMContentLoaded : HTML이 전부 로드 및 처리되어 DOM 생성이 완료되었을 때

CSS 이벤트

  • transitionend : CSS 애니메이션이 종료되었을 때

이 중에서 마우스와 키보드 이벤트를 살펴보면

"버튼을 누를 때" 와 "버튼을 뗄 때" 두 가지 이벤트가 존재한다.

 

이는 단순히 이벤트를 binding할 때 간과할 수 있는 부분인데, 예를 들어 키 입력에 대해 이벤트를 바인딩 한다고 가정해보자.

 

keydown으로만 이벤트를 바인딩 했을 때 다음과 같은 경우를 생각해 볼 수 있다.

  1. 'A'키를 누른 상태에서 때지 않고
  2. 'B'키를 입력하는 경우

즉 이벤트의 순서가 꼭 down > up > down > up 의 순서가 아닐수도 있는 것이다.

Event listener

브라우저는 Event를 발생시켜준다. 개발자는 그때 할 동작을 등록할 수 있다.

다시 말해, HTML엘리먼트별로 어떤 이벤트(주로 키보드나 마우스 관련)가 발생했을 때 특정 행위를(어떤 일) 하고 싶다면, 대상엘리먼트를 찾고 어떤 일을 등록하면 된다.

 

간단한 코드부터 살펴보자

var target = document.querySelector(".target");

target.addEventListener("click", function(e){
  console.log(e);
}, false);

https://developer.mozilla.org/ko/docs/Web/API/EventTarget/addEventListener

 

EventTarget.addEventListener()

EventTarget의 addEventListener() 메서드는 지정한 이벤트가 대상에 전달될 때마다 호출할 함수를 설정합니다.

developer.mozilla.org

위 코드에서 false 부분은 option이다. option의 의미는 MDN 문서를 통해 알아볼 수 있다.

 

예제에 사용한 false 는 capture속성이다.

 

capture : DOM 트리의 하단에 있는 EventTarget 으로 전송하기 전에, 등록된 listener 로 이 타입의 이벤트의 전송여부를 나타내는 Boolean 입니다.

 

그렇다면 다음 코드에 인자로들어가는 함수 function의 인자 e는 무엇일까?

 

이벤트 객체

 

위 코드를 실행시키기 위해 다음과 같은 html 파일을 제작하자

 

<html>
<body>
  <div id="target">aa</div>
</body>

<script>
  var el = document.getElementById("target");
  
  el.addEventListener("click", function(event){
   console.log(event);
  }, false);
</script>
</html>

콘솔에는 다음과 같이 출려된다.

MouseEvent {isTrusted: true, screenX: 1008, screenY: 153, clientX: 16, clientY: 19, …}

 

이 중에서 가장 많이 사용하는것은 Event 객체의 target, currentTarget property이다.

Event.target은 이벤트가 발생한 element를 나타낸다.

 

그렇다면 currentTarget은 무엇일까?

Event.currentTarget의 경우 이벤트가 바인딩된 요소, 해당하는 요소를 반환한다.

 

아래의 예제를 살펴보자

<div onclick="checkTarget();">
  <span>test</span>
</div>

<script>
function checkTarget(event) {
  var el = event.currentTarget;
  console.log(el);
}
</script>

만약 사용자가 div 내부의 span 태그를 클릭한 경우 각각은 다음과 같다.

 

Event.target : 클릭된 span 태그

Event.currentTarget : 이벤트가 바인딩된 div 요소를 반환

 

만약 이벤트를 binding한 곳과 클릭한 곳의 depth가 깊어지는 경우 Event.target 만으로는 어떤 요소가 클릭되어 반환되어야하는지 알기 쉽지 않다.

이 경우 currentTarget을 이용해 이벤트가 바인딩 된 곳을 알 수 있다.

이벤트 버블링 (전파)

다음과 같은 구조를 생각해보자

 

Wijmo HTML Events Capturing and Bubbling

Element 1, Element 2, Element 3모두에 이벤트 리스너를 등록한 상태에서, Element 3 를 클릭한 경우에는 어떻게 될까?

Element 3는 Element 2에 속하고, Element 2는 Element 1 에 속하기 때문에 3개의 이벤트가 발생한다.

 

이것을 이벤트 전파라고 한다.

 

이벤트 전파는 버블링과 캡처링 방식 두 가지 방식으로 동작한다.

클릭한 지점이 하위엘리먼트 이더라도, 그것을 감싸고 있는 상위 엘리먼트까지 올라가면서 이벤트리스너가 있는지 찾는 과정이다. 

 

다음의 경우를 생각해 보자

<ul>
  <li>
    <div>
    	<!-- something 1 -->
    </div>
  </li>
  <li>
    <div>
    	<!-- something 2 -->
    </div>
  </li>
  <li>
    <div>
    	<!-- something 3 -->
    </div>
  </li>
</ul>

위와 같은 구조에서 각 li 태그마다 이벤트 리스너를 직접 할당해 줄 수 있다.

그러나 이 경우 브라우저는 li 태그의 갯수만큼 이벤트 리스너를 기억하고 있어야 한다.

 

이 경우 다음과 같은 방법으로 최적화 할 수 있다.

  1. 최 상위 태그에 이벤트리스너를 등록하고
  2. Event.target을 이용해 분기처리 (각각의 li태그를 의미하기 때문에)

단순히 정적인 웹을 표기하고자 한다면 이벤트는 필요 없다. 그러나 동적인 웹을 제작하기 위해선 이벤트는 필수적이다.

 

그러나 브라우저가 너무 많은 이벤트핸들러를 기억하고 있는 것은 자원의 낭비일수도 있다.

 

따라서 브라우저가 너무 많은 이벤트핸들러를 기억하지 않게 하고, DOM이 추가되거나 삭제 될때 Event등록을 매번 해주지 않도록 최적화 하는 과정이 필요하다.

 

 

자바스크립트의 변수, 함수에는 스코프가 존재한다.

스코프는 자바스크립트에서 어떤 변수들에 접근할 수 있는지를 나타낸다.

 

ES5 까지는 함수 레벨의 스코프(function scope)만 사용 가능했으나,

ES6 부터는 let과 const로 블록 레벨의 스코프(block scope)를 사용할 수 있다.

 

이 스코프에 대해서 알아보자

 

https://www.edwith.org/boostcourse-web/lecture/16693/

 

[LECTURE] 1) 자바스크립트 변수-연산자-타입 : edwith

들어가기 전에 컴파일 단계가 없는 자바스크립트의 type(형)은 실행단계에서 타입이 결정됩니다. 변수선언은 어떻게 정의하고, 자바스크립트의 타입은 어떤 것들이 있는지 확인해봅니다.... - 부스트코스

www.edwith.org


스코프와 레벨

스코프는 다음과 같이 구성된다

  • 전역 스코프
  • 지역 스코프
    • 함수 레벨 스코프
    • 블록 레벨 스코프

앞서 블록 레벨 스코프, 함수 레벨 스코프를 설명했는데 전역 스코프와 지역 스코프는 무엇인가?

 

아래 내용을 보며 살펴보도록 하자

전역 스코프

변수가 함수 바깥이나 {} 바깥 에서 선언되었다면, 전역 스코프에 정의된다.

let a = 'aa'

위의 a는 어디에서나 접근 가능하다.

 

변수를 글로벌 변수로 선언했을 경우, 이는 전역 스코프에 정의된다고 알 수 있다.

 

let a = 'first'
let a = 'second' // 이미 선언되어있음

전역 스코프에서 중복 재할당의 문제가 발생할 수 있으므로 주의해야 한다.

 

지역 스코프

지역 스코프는 특정 영역에서만 사용할 수 있는 변수이다.

지역 스코프는 다음과 같이 2가지로 이루어진다

  • 함수 레벨
  • 블록 레벨

함수 레벨 스코프

function a(){
  var b = 2;
}

위와 같이 선언했을 때, b는 함수 a에서만 사용할 수 있다.

함수 레벨 스코프는, 함수 내에서만 사용 가능한 변수를 의미한다.

 

함수 내에서 선언된 변수는 함수 내에서만 유효하며 함수 외부에서는 참조할 수 없다.

즉, 함수 내부에서 선언한 변수는 지역 변수이며 함수 외부에서 선언한 변수는 모두 전역 변수이다.

 

블록 레벨 스코프

블록 내부에서 const, let으로 변수를 선언한다면, 이 변수들은 블록 내부에서만 사용이 가능하다.

{
  const a = 'hello world'
  console.log(a) // 'hello world'
}
console.log(a) // Error, a is not defined

모든 코드 블록(함수, if 문, for 문, while 문, try/catch 문 등) 내에서 선언된 변수는 코드 블록 내에서만 유효하다.

따라서 코드 블록 외부에서는 참조할 수 없다.

 

즉, 코드 블록 내부에서 선언한 변수는 지역 변수이다.


정리하자면 javascript는 ES5까지는 함수 레벨 스코프만 제공했으나,

ES6부터는 let, const를 이용해 블록 레벨 스코프 선언이 가능하다.

 

const를 먼저 사용하자. 재할당해야 하는 경우가 생기면 let을 사용한다.

 

var는 block scope를 지원하지 않기 때문에 되도록 사용하지 말자

 

앞의 글에서 자바스크립트에는 타입이 다음과 같은 것들이 존재한다고 설명했다.

undefined, null, boolean, number, string, object, function, array, Date, RegExp

 

  • 자바스크립트에서 타입은 선언할 때가 아니고, 실행타임에 결정된다. (실제 그 타입의 변수가 실행되는 경우)
  • 함수 안에서의 파라미터나 변수는 실행될 때 그 타입이 결정된다

위 성질은 자바스크립트가 컴파일을 총 2번 하기 때문에 일어난다.

자세한 컴파일 과정은 다음과 같다.

  1. 함수, 변수들 호이스팅하며 선언한다.
  2. 선언된 객체들에게 값을 할당한다.

몇몇 타입들은 typeof 를 이용해 타입을 검사할 수 있다.

  • undefined : 변수가 정의되지 않거나 값이 없을 때
  • number : 데이터 타입이 수일 때
  • string : 데이터 타입이 문자열일 때
  • boolean : 데이터 타입이 불리언일 때
  • object : 데이터 타입이 함수, 배열 등 객체일 때
  • function : 변수의 값이 함수일 때
  • symbol : 데이터 타입이 심볼일 때

심볼 타입

위 타입들 중 대부분은 이해가 가능하지만, 심볼 타입은 도데체 무엇일까?

 

심볼은 es6에서 추가된 새로운 타입이다.

유일한 객체의 프로퍼티 키(property key)를 만들기 위해 사용한다.

 

key로 사용했을 때, 다른것들과 절대 충돌이 나지 않는 점을 이용한다.

 

ES6의 class에서 private한 객체를 만들 때 사용할 수 있다.

const Count = (() => {
  const count = Symbol('COUNT');
  class Count {
    constructor() {
      this[count] = 0;
    }
    getScore() { return this[count]; }
    setScore(score) { this[count] = score; }
  }
  return Count;
})();

const test = new Count();

위와 같이 선언했을 때, test.count에 접근할 수 없다.

 

하지만 이 방법으로 완전히 private한 요소를 만들 수 있는 것은 아니다.

다음과 같은 방법으로 test.count에 접근할 수 있다.

const testSymbol = Object.getOwnPropertySymbols(test)[0];
test[testSymbol] = 20 // this is count

원시 타입 vs 참조 타입

위 타입을 기본형(원시 타입)참조형(참조 타입)으로 나눌 수 있는데 이는 C언어에서 call by value, call by reference의 차이로 이해하면 쉽다.

 

원시 타입 (Primitive) : call by value

  • Number
  • String
  • Boolean
  • null
  • undefined

참조 타입 (Reference) : call by reference

  • Object
  • Array
  • Function
  • RegExp

두 타입의 차이를 알아보기 위해 다음의 예제를 실행해보자

// 원시 타입의 경우
let a = 3;
let b = a;

b = 2;	// 2
a	// 3

// 참조 타입의 경우
let objA = { value : 3 }
let objB = objA

objB.value = 2;
objA	// {value: 2}

objA는 객체 (Object)타입 이므로 objB = objA 를 수행했을 때, objB는 objA의 주소를 가진다.

 

그렇다면 참조 타입에서 '값 복사'를 하려면 어떻게 해야 할까?? (주소를 복사하지 않음)

 

Object.assign()을 이용한다. (객체의 depth가 1단계만일때)

function cloneObject(obj) { 
  return Object.assign({}, obj); 
}

위 함수의 경우 obj의 depth가 1단계 만이라면, (최대 depth가 1단계) 객체를 값 복사 할 수 있다!

 

다음과 같은 객체의 경우 유효하다.

 

// 자식들이 원시 타입이다.
let obj = {
  child1 : 10,
  child2 : "hello",
  child3 : undefined,
  child4 : null
}

허나 Object.assign의 경우 자식이 참조 타입인 경우 자식에 대한 복사는 다시 참조 복사를 해버리는 문제가 발생한다.

이러한 복사를 얕은 복사 라고 한다.

 

이 경우 다음 방법을 이용한다.

 

JSON.parse() & JSON.stringify()을 이용한다.

JSON.stringify(obj)는 obj의 형태를 문자열로 치환해준다.

let obj = {
  child1 : 10,
  child2 : "hello",
  child3 : undefined,
  child4 : null
}

JSON.stringify(obj) // "{"child1":10,"child2":"hello","child4":null}"

JSON.parse("string")의 경우 "string"을 객체로 복구한다.

let str = JSON.stringify(obj)
JSON.parse(str) // {child1: 10, child2: "hello", child4: null}

두 메소드를 합치면 객체를 깊은 복사 할 수 있다.

허나 이 방법은 매우 느리므로 정말 깊은 복사를 해야 할 때만 이용하도록 하자.

(문자열 치환후 다시 객체로 복구하므로...)

 

함수의 반환 타입은 무엇인가?

function printName(firstname) {
    var myname = "jisu";
    var result = myname + " " +  firstname;
}

위 코드를 실행했을 때, printName의 반환값은 무엇일까?

답은 undefined이다.

 

자바스크립트 함수는 반드시 return값이 존재하며, 없을 때는 기본 반환값인 'undefined'를 반환한다.

 


실제 개발을 해보다 보면, 자바스크립트의 타입 때문에 생기는 에러가 자주 발생한다.

다음 객체를 비동기로 받아 사용한다고 생각해보자.

let res = {
  hello : "world"
}

만약 API에서 res를 제대로 받아온다면 res.hello를 실행했을 때 문제가 없을 것이다.

그러나 res를 제대로 받아오지 못한다면 (res가 undefined)라면 res.hello는 undefined일 것이다.

 

이 경우 res.hello는 원시타입이므로 큰 문제가 발생하지 않을 수 있지만 함수등의 경우는 어떨까?

 

let res = {
  func : () => { // do something }
}

위 경우 res가 undefined인 상태에서 res.func()를 실행하려고 한다면 에러가 발생한다.

 

이런 타입과 관련한 에러를 직접, 실행하던 도중에 발견한다면 찾는데 시간이 오래 걸린다.

 

자바스크립트 타입에 관련한 에러를 컴파일시 발견할 수 있게 만든것이 타입스크립트다.

 

타입스크립트

 

https://www.typescriptlang.org/

 

TypeScript - JavaScript that scales.

State of the art JavaScript TypeScript offers support for the latest and evolving JavaScript features, including those from ECMAScript 2015 and future proposals, like async functions and decorators, to help build robust components. These features are avail

www.typescriptlang.org

 

node를 사용하고 있다면 다음 명령을 통해 설치할 수 있다.

 

npm install -g typescript

 

타입스크립트와 자바스크립트는 다음과 같은 차이가 존재한다.

 

var a = 1; // number
var b = '2'; // string
console.log(a+b) // "12"
var a:number = 1; 
var b:string = '2'; 
console.log(a+b)

첫 번째 코드는 javascript 코드이다. a와 b가 다른타입인데 + 연산을 수행하고, 이 연산이 문자열의 합을 출력한다.

이는 생각보다 자주 발생할 수 있는 문제인데, 특히 숫자의 경우 문자열로 처리한 뒤 저장할 수 있기 때문이다.

 

타입스크립트에서는 a와 b의 타입을 지정해 줄 수 있으므로 연산 전에 에러를 발생시킨다.

 


 

대부분의 초보자가 자바스크립트를 접할 때 가장 난해하게 여기는 것이 바로 타입이라고 생각한다.

특히 처음 배울 때 변수에 어떤 값이던 할당할 수 있다는 점은 복잡한 프로그램을 개발하기 어렵게 한다.

 

실제 로직을 구현했다 하더라고 타입때문에 에러가 발생하는 경우 이를 파악하기 힘들 수도 있다.

 

만약 자바스크립트에 한계를 느끼기 시작했다면, 타입스크립트로 옮겨갈 기회이다!

자바스크립트 언어는 현재 매우 많은곳에 쓰이고 있다.

 

웹 개발자로서 백엔드, 프론트엔트를 가리지 않고 자바스크립트 만으로 개발을 할 수 있을 정도다.

(예를 들면 node express server + react)

 

특히 브라우저에서 자체적으로 자바스크립트를 지원해주기도 하고,

react나 vuejs등을 사용하는 경우는 전부 자바스크립트이다.

 

그리고 자바스크립트에서 '타입'을 지정해주는 타입스크립트 언어까지 나온 상태이니

자바스크립트만 제대로 할 줄 알아도 큰 이점이 된다.

 

글을 작성하는 시점에서 (2020.02.17) 티오베(TIOBE)에서 자바스크립트 언어의 순위를 확인해보니 7위를 기록하고 있었다.

 

그러면 다른언어와 구별되는 자바스크립트의 특징과, 사용법을 알아보자.

 

강의 링크

 

[LECTURE] 1) 자바스크립트 변수-연산자-타입 : edwith

들어가기 전에 컴파일 단계가 없는 자바스크립트의 type(형)은 실행단계에서 타입이 결정됩니다. 변수선언은 어떻게 정의하고, 자바스크립트의 타입은 어떤 것들이 있는지 확인해봅니다.... - 부스트코스

www.edwith.org


hello world

console.log("hello world");	// 이것도 되고
console.log('hello world')	// 이것도 된다

자바스크립트를 처음 배울 때 특이했던 점 중 하나는 바로 ; (세미콜론) 이 필요가 없다는 것이다.

 

그리고 C언어처럼 변수의 형태를 지정해 줄 필요가 없다. (var, let, const 는 scope를 설정)

 

자바스크립트 언어를 직접 확인해보고 싶은가??

 

크롬을 사용한다면 F12 (개발자 도구)를 열고 console 탭으로 진입하자!

 

개발자 도구에서 자바스크립트를 사용해 볼 수 있다.

크롬이 아니더라도 파이어폭스, 인터넷 익스플로러, 엣지 브라우저 등등 대부분의 브라우저에서 자바스크립트를 이용해 볼 수 있다.

 

만약 브라우저가 아닌 터미널에서 코드를 실행시키고 싶다면??

 

Node.js를 설치하는 것을 추천한다!

 

https://nodejs.org/ko/

 

Node.js

Node.js® is a JavaScript runtime built on Chrome's V8 JavaScript engine.

nodejs.org

Node.js가 설치되었는지 확인하고 싶다면 터미널에서 다음을 실행해보자

node -v

제대로 설치되었다면 버전정보가 나타난다.

설치가 완료되었다면 실행하고 싶은 자바스크립트 코드를 작성한다.

파일명을 a.js라고 했을 때 다음과 같이 실행하자

 

// a.js
console.log("hello world");

a.js 파일이 존재하는 위치에서 node a.js를 실행하면 a.js가 실행횐다.

자바스크립트 문법

다음 코드를 살펴보자

var a = 2;
var a = "aaa";
var a = 'aaa';
var a = true;
var a = [];
var a = {};
var a = undefined;

a는 여러번 선언되었고, 각 경우마다 데이터 타입이 다르다.

그러나 이는 전혀 문제를 일으키지 않는다.

 

사실 자바스크립트를 이루고 있는 모든것이 객체이다.

 

일단 모든 것이 객체이기 때문에 형태가 달라질 수 있다고 생각하자.

 

다음 코드를 실행해보자

 

var a;
console.log(a);	// undefined

도데체 이 undefined는 무엇인가??

 

undefined는 값이 할당되지 않은 상태이다. 이는 null과 다르다

 

undefined === null	// false
undefined == null	// true

직접 테스트해보자

위 예제는 자바스크립트에서 == 연산대신 === 연산을 사용해야 하는 중요한 이유 중 하나이다.

 

== 는 두 객체의 '값'이 같은지 확인하는 연산이다.

=== 는 두 객체의 '값'과 '타입'이 같은지 확인하는 연산이다.

 

typeof null		// "object"
typeof undefined	//"undefined"

그러면 자바스크립트에는 어떤 타입들이 존재할까?

 

  • undefined
  • null
  • boolean
  • number
  • string
  • object
  • function
  • array
  • Date
  • RegExp

여기까지 '대략 이것이 자바스크립트' 이다라는 내용의 글이였다.

다음에는 자바스크립트 type들의 성질에 대하여 알아보자.

+ Recent posts