<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>boori.log</title>
        <link>https://velog.io/</link>
        <description></description>
        <lastBuildDate>Thu, 08 Sep 2022 08:37:31 GMT</lastBuildDate>
        <docs>https://validator.w3.org/feed/docs/rss2.html</docs>
        <generator>https://github.com/jpmonette/feed</generator>
        <image>
            <title>boori.log</title>
            <url>https://velog.velcdn.com/images/cho-boori/profile/bfd8ef75-0cfb-483a-9b1a-a6c6e7fda4ae/social_profile.jpeg</url>
            <link>https://velog.io/</link>
        </image>
        <copyright>Copyright (C) 2019. boori.log. All rights reserved.</copyright>
        <atom:link href="https://v2.velog.io/rss/cho-boori" rel="self" type="application/rss+xml"/>
        <item>
            <title><![CDATA[JavaScript - var, let과 호이스팅]]></title>
            <link>https://velog.io/@cho-boori/JavaScript-var-let%EA%B3%BC-%ED%98%B8%EC%9D%B4%EC%8A%A4%ED%8C%85</link>
            <guid>https://velog.io/@cho-boori/JavaScript-var-let%EA%B3%BC-%ED%98%B8%EC%9D%B4%EC%8A%A4%ED%8C%85</guid>
            <pubDate>Thu, 08 Sep 2022 08:37:31 GMT</pubDate>
            <description><![CDATA[<p>오늘은 계속 봐도 계속 혼돈이 왔던 var, let + 호이스팅에 대해 기록해보려고 한다.</p>
<h4 id="호이스팅이란-🤷🏻♀️">호이스팅이란? 🤷🏻‍♀️</h4>
<p>자바스크립트 엔진이 코드를 실행하기 전, <code>변수선언/함수선언</code>을 해당 스코프의 최상단으로 끌어 올리는 것을 말한다. (메모리에 먼저 선언)</p>
<ul>
<li>모든 선언은 호이스팅이 일어난다. </li>
<li>할당이 아닌 선언이다. 값 할당은 포함되지 않는다.</li>
</ul>
<br>

<h3 id="var">var</h3>
<p>var, let, const 중 가장 먼저 세상에 나온 <code>var</code> 
<strong>문제1)</strong></p>
<pre><code>console.log(name);
var name = &#39;jane&#39;;
console.log(name);</code></pre><p>첫번째 줄에서 name을 선언하기 전에 name을 출력하고 있지만, 에러가 나지 않는다.
그 이유는, 자바스크립트 엔진을 통해 name 변수가 호이스팅 되었기 때문이다. (메모리에 <code>name</code> 이라는 변수가 있기 때문)</p>
<ul>
<li>var는 호이스팅 시 선언과 함께 undefined로 <code>초기화</code> 도 함께된다.</li>
</ul>
<p><strong>문제2)</strong></p>
<pre><code>for(var i=0; i&lt;5; i++) {
    console.log(i);
}
console.log(i);</code></pre><p>마지막 출력 결과는 5이다. for문 안에서 사용하던 변수를 밖에서 출력해도 오류가 나지 않는다.
그 이유는, <code>var</code> 변수는 지역변수와 전역변수의 개념이 확실하지 않다.</p>
<ul>
<li>var에서는 함수를 제외한 모든 변수들은 전역변수로 호이스팅이 된다. (함수는 지역변수로 호이스팅)</li>
<li>for, if 문 안에서 작성한 변수도 모두 전역변수로 호이스팅 되어 밖에서 사용해도 오류가 나지 않는다.<br>

</li>
</ul>
<h3 id="let">let</h3>
<p>이러한 <code>var</code> 의 문제 때문에 새로운 변수 선언 방식인 <code>let</code> 이 등장하게 되었다.
var를 let으로 바꾸어 다시 실행해본다면?
<strong>문제1</strong> 에서는 초기화 전에 name에 접근할 수 없다는 오류가 발생하며,
<strong>문제2</strong> 에서는 i가 정의되지 않았다 는 오류가 발생한다.</p>
<h4 id="let에서의-호이스팅">let에서의 호이스팅?</h4>
<p>let 변수도 호이스팅이 된다. 그런데 TDZ (Temporal Death Zone)이라는 개념이 더해졌다.
<code>TDZ 개념을 적용해본다면</code>, 변수가 호이스팅이 되었어도 변수 할당이 되기 전까진 해당 변수에 접근할 수 없다는 것이다. =&gt; 일시적으로 <strong>문제1</strong> 의 첫번째줄은 Death Zone이 되는것!</p>
<ul>
<li>let 변수는 호이스팅 시 초기화를 하지 않는다.</li>
<li>스코프의 시작 점부터 초기화 시작 지점까지의 구간을 <code>일시적 사각지대 (TDZ)</code> 라고 부른다.</li>
</ul>
<br>
[참고 강의]

<p><a href="https://www.youtube.com/watch?v=fETYLCU2YYc">자바스크립트 let,var 를 아직도 모른다고?</a></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[#3 LSP, ISP]]></title>
            <link>https://velog.io/@cho-boori/clean-architecture</link>
            <guid>https://velog.io/@cho-boori/clean-architecture</guid>
            <pubDate>Fri, 26 Aug 2022 12:11:33 GMT</pubDate>
            <description><![CDATA[<h1 id="lsp-리스코프-치환-원칙">LSP: 리스코프 치환 원칙</h1>
<p>바바라 리스코프가 정의한 하위 타입</p>
<blockquote>
<ul>
<li>S 타입의 객체 o1에 대응하는 T타입 객체 o2가 있다. → **<code>o1: S, o2: T</code></li>
<li>** T 타입을 이용해 정의한 모든 프로그램 P에서 <code>o2 → o1</code> 치환하더라도 P의 행위가 변하지 않는다면, 
  S는 T의 하위 타입이다.</li>
</ul>
</blockquote>
<h3 id="✅-예시를-통해-알아보는-리스코프-치환-원칙">✅ 예시를 통해 알아보는 리스코프 치환 원칙</h3>
<hr>
<p><strong>1) 상속을 사용하도록 가이드하기 - LSP 준수 설계</strong>
<img src="https://velog.velcdn.com/images/cho-boori/post/0d185568-4f97-405e-881c-50b2085352f5/image.png" alt=""></p>
<ul>
<li>Billing 애플리케이션의 행위가 License (인터페이스) 하위 타입 중 무엇을 사용하는지에 전혀 의존하지 않음</li>
<li>하위 타입은 모두 License 타입을 <strong>치환</strong> 할 수 있음</li>
</ul>
<p>⇒ <strong>LSP 준수 설계</strong></p>
<p><strong>2) 정사각형/직사각형 문제 - LSP 위반!</strong>
<img src="https://velog.velcdn.com/images/cho-boori/post/ab671834-02e8-42cc-9f6a-e46e9c65168c/image.png" alt=""></p>
<ul>
<li>Square는 Rectangle의 하위 타입으로 적합하지 않음<ul>
<li>Rectangle의 높이와 너비는 독립적으로 변경될 수 있지만,
Square의 높이와 너비는 반드시 함께 변경되기 때문임</li>
</ul>
</li>
<li>따라서 User는 사용과정에서 혼동이 생길 수 있음</li>
<li>해결 방법: 조건문 등을 이용해 Rectangle이 실제로는 Square인지 검사<ul>
<li>하지만 이렇게 되면 결국 User의 행위가 사용하는 타입에 의존하게 되므로,
서로 타입을 치환할 수 없게 됨</li>
</ul>
</li>
</ul>
<p>⇒ <strong>LSP 위반 설계</strong></p>
<pre><code class="language-java">public class Rectangle {
    private int width;
    private int height;

    public void setWidth(int width) {
        this.width = width;
    }

    public void setHeight(int height) {
        this.height = height;
    }

    public int getWidth() {
        return width;
    }

    public int getHeight() {
        return height;
    }

        public int getArea() {
        return width * height;
    }
}

public class Square extends Rectangle {

    @Override
    public void setWidth(int width) {
        super.setWidth(width);
        super.setHeight(width);
    }

    @Override
    public void setHeight(int height) {
        super.setWidth(height);
        super.setHeight(height);
    }
}</code></pre>
<pre><code class="language-java">Rectangle square = new Square();
square.setWidth(5);
square.setHeight(2);
assert(square.getArea() == 10);</code></pre>
<ul>
<li>자식 클래스가 부모 클래스를 대신하였을 때 의도에 맞게 동작하지 않음 → <em>리스코프 치환 원칙 위반</em></li>
</ul>
<p>⇒ <strong>직사각형, 정사각형 상속 관계를 끊고 상속관계 재정의</strong></p>
<p>⇒ <strong>getArea 메서드를 자식 클래스로 옮기는 방법 등이 필요</strong></p>
<h3 id="✅-lsp와-아키텍처">✅ LSP와 아키텍처</h3>
<hr>
<ul>
<li>LSP는 인터페이스와 구현체에도 적용됨</li>
<li>아키텍처 관점에서 LSP를 이해하는 최선의 방법은,
이 원칙을 어겼을 때 시스템 아키텍처에서 무슨 일이 일어나는지 관찰하는 것</li>
</ul>
<h3 id="✅-lsp-위배-사례---아키텍처-관점의-lsp">✅ LSP 위배 사례 - 아키텍처 관점의 LSP</h3>
<hr>
<p><strong>상황</strong></p>
<ul>
<li><p>택시 파견 서비스</p>
<ul>
<li><p>기사 선택 → 해당 기사의 URI 정보를 얻은 후 → 그 URI를 이용해 해당 기사를 고객 위치로 파견</p>
</li>
<li><p>URI에 파견에 필요한 정보를 덧붙인 후, PUT 방식으로 호출</p>
<pre><code>  purplecab.com/driver/Bob
                      /pickupAddress/24 Maple St.
                      /pickupTime/153
                      /destination/ORD</code></pre></li>
</ul>
</li>
</ul>
<p><strong>이 예제에서 말하고자 하는 것</strong></p>
<ul>
<li>다양한 택시업체에서 파견 서비스를 만들 때, 동일한 REST 인터페이스를 반드시 준수해야함</li>
<li>일부 업체에서 다르게 처리한다면, if문 등의 방법으로 해결해야함. 이런 예외 상황은 끊임없이 발생</li>
<li>아키텍트는 이러한 버그로부터 시스템을 보호 해야함<ul>
<li>파견 URI를 키로 사용해 파견 요청 포맷을 관리</li>
<li>각 REST 서비스들의 인터페이스가 서로 치환 가능하지 않다는 사실을 처리하는 복잡한 메커니즘을 추가해야 함</li>
</ul>
</li>
</ul>
<table>
<thead>
<tr>
<th align="left">URI</th>
<th align="center">Dispatch Format</th>
</tr>
</thead>
<tbody><tr>
<td align="left">Acme.com</td>
<td align="center">/pickupAddress/%s/pickupTime/%s/dest/%s</td>
</tr>
<tr>
<td align="left"><em>.</em></td>
<td align="center">/pickupAddress/%s/pickupTime/%s/destination/%s</td>
</tr>
<tr>
<td align="left"><br></td>
<td align="center"></td>
</tr>
</tbody></table>
<h3 id="✅-결론">✅ 결론</h3>
<hr>
<ul>
<li>치환 가능성을 조금이라도 위배할 경우 시스템 아키텍처가 오염되어, 상당량의 별도 메커니즘을 추가해야할 수도 있음</li>
<li>따라서 LSP는 아키텍처 수준까지 확장할 수 있고, 위와 같은 문제를 막으려면 반드시 확장해야 함<br>
</li>
</ul>
<hr>
<h3 id="isp-인터페이스-분리-원칙">ISP: 인터페이스 분리 원칙</h3>
<p><img src="https://velog.velcdn.com/images/cho-boori/post/625ef979-8904-400c-869f-0d44690cc0db/image.png" alt=""></p>
<ul>
<li><p><strong>OPS</strong>: 정적 타입 언어로 작성된 클래스</p>
</li>
<li><p><code>User1: op1</code>, <code>User2: op2</code>, <code>User3: op3</code></p>
</li>
<li><p>User1은 op2, op3를 전혀 사용하지 않음에도 User1은 op2, op3에 의존하게 됨</p>
<p>  → op2, op3의 코드가 변경되면 User1도 재컴파일 후 배포 ⭕️</p>
</li>
</ul>
<p><strong>⇒ 인터페이스 분리 원칙 위반</strong></p>
<h3 id="✅-해결-방법---인터페이스-단위로-분리">✅ 해결 방법 - 인터페이스 단위로 분리</h3>
<hr>
<p><img src="https://velog.velcdn.com/images/cho-boori/post/2812405b-567f-4685-9969-b1fc9b31fad2/image.png" alt=""></p>
<ul>
<li><p>OPS를 상속받는 U1Ops, U2Ops, U3Ops를 인터페이스 단위로 분리</p>
</li>
<li><p>User1은 U1Ops, op1에는 의존하지만 OPS에는 의존하지 않게 됨</p>
<p>  → OPS의 변경이 User1과 관계없다면, 재컴파일/배포 ❌</p>
</li>
</ul>
<p>⇒ <strong>인터페이스 분리 원칙 준수</strong></p>
<h3 id="✅-인터페이스-분리-원칙-위반-예제">✅ 인터페이스 분리 원칙 위반 예제</h3>
<hr>
<pre><code class="language-java">public interface MultifunctionService {
  void copy();
  void fax(Address from, Address to);
  void print();
}</code></pre>
<pre><code class="language-java">public class CopyMachine implements MultifunctionService {
  @Override
  public void copy() {
    System.out.println(&quot;### 복사 ###&quot;);
  }

  @Override
  public void fax(Address from, Address to) {
    // 사용하지 않는 인터페이스가 변경되어도 함께 수정이 일어난다.
  }

  @Override
  public print() {
    // 사용하지 않는 인터페이스가 변경되어도 함께 수정이 일어난다.
  }
}</code></pre>
<ul>
<li>만약 <code>multinfunction</code> 인터페이스에서 fax()나 print()에 대해서 리턴 타입이 변경된다면, 이와 전혀 상관없는 CopyMachine 클래스도 같이 수정해줘야 하는 문제가 발생한다.</li>
</ul>
<h3 id="✅-해결방법">✅ 해결방법</h3>
<pre><code class="language-java">public interface Print{
  void print();
}

public interface Copy {
  void copy();
}

public interface Fax {
  void fax(Address from, Address to);
}</code></pre>
<pre><code class="language-java">public class copyMachine implements Copy {
  @Override
  void copy() {
    System.out.println(&quot;### 복사 ###&quot;);
  }
}</code></pre>
<ul>
<li><p>Print, Copy, Fax 인터페이스로 분리</p>
<p>⇒ <code>copyMachine</code> 과 관계없다면 print(), fax()가 변경되어도 재컴파일/배포하지 않아도 됨</p>
<p>⇒ <strong>인터페이스 분리 원칙 준수</strong></p>
<br>

<h3 id="✅-isp와-언어">✅ ISP와 언어</h3>
</li>
</ul>
<hr>
<ul>
<li>ISP는 아키텍처가 아니라, 언어와 관련된 문제라고 결론내릴 여지가 있음<ul>
<li><strong>정적 타입 언어</strong>는 <code>import, include</code> 선언문으로 인해 코드 의존성 발생,
재컴파일/재배포가 강제되는 상황 초래</li>
<li><strong>동적 타입 언어</strong>는 코드 의존성 ❌ , 재컴파일/재배포가 필요하지 않음
a. 참고할 사항<ul>
<li>자바는 정적 타입 언어이지만 재컴파일/재배포 하지 않는 경우가 있음. 자바는 <code>비-final, 비-private, 인스턴스 변수</code>에 대해서는 동적 바인딩을 수행하기 때문</li>
</ul>
</li>
</ul>
</li>
</ul>
<blockquote>
<p>호출할 정확한 메서드를 런타임에 결정하는 것
            (정적 바인딩 → 컴파일링시에 결정)</p>
</blockquote>
<p> ⇒ 따라서 ISP는 언어 종류에 따라 영향받는 정도가 다름
 <br></p>
<h3 id="✅-isp와-아키텍처">✅ ISP와 아키텍처</h3>
<hr>
<p><img src="https://velog.velcdn.com/images/cho-boori/post/3e75a2a1-cd64-44a2-bfa2-2c243ad6f6c0/image.png" alt=""></p>
<ul>
<li>시스템 S → F 프레임워크 사용  /  F 프레임워크 → 데이터베이스 D를 사용</li>
<li><code>S → F → D</code> 의존 관계</li>
<li>S와 전혀 관계없는 기능이 D에 포함된 경우<ul>
<li>D 변경 시 → S, F 재배포해야할 수도 있는 문제</li>
<li>D 내부 기능 중 문제가 발생했을 때 → S, F에도 영향을 미치는 문제</li>
</ul>
</li>
</ul>
<br>

<h3 id="✅-결론-1">✅ 결론</h3>
<hr>
<ul>
<li>클라이언트는 사용하지 않는 메소드에 의존하지 않아야함 → 불필요한 의존성 제거</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[#27 '크고 작은 모든' 서비스들]]></title>
            <link>https://velog.io/@cho-boori/27-%ED%81%AC%EA%B3%A0-%EC%9E%91%EC%9D%80-%EB%AA%A8%EB%93%A0-%EC%84%9C%EB%B9%84%EC%8A%A4%EB%93%A4</link>
            <guid>https://velog.io/@cho-boori/27-%ED%81%AC%EA%B3%A0-%EC%9E%91%EC%9D%80-%EB%AA%A8%EB%93%A0-%EC%84%9C%EB%B9%84%EC%8A%A4%EB%93%A4</guid>
            <pubDate>Fri, 26 Aug 2022 11:55:46 GMT</pubDate>
            <description><![CDATA[<p>아키텍처 관점으로 중요한 서비스도 있지만, 그렇지 않은 서비스도 존재한다. 
→ 저자는 중요한 서비스에 대해 관심을 가진다.</p>
<h3 id="서비스의-이점">서비스의 이점?</h3>
<hr>
<p>서비스 아키텍처에 대해 이의 제기.</p>
<p><strong>결합 분리의 오류</strong></p>
<p>이점1. 서비스를 분리함으로써 통해 상호 결합이 확실히 분리된다고 본다.</p>
<p>그러나 서비스 프로세서의 네트워크 상 공유 자원 때문에 결합될 가능성은 여전히 존재한다.</p>
<ol>
<li>공유되는 데이터 레코드에 새로운 필드를 추가한다면, 필드를 사용하는 서비스는 반드시 변경되어야한다.</li>
<li>서비스들은 이 필드에 담긴 데이터를 해석하는 방식을 사전에 완벽하게 조율해야한다.</li>
</ol>
<p>따라서 서비스들은 레코드에 강하게 결합되고, 서비스들 사이는 간접적으로 결합되어 버린다.</p>
<p><strong>개발 및 배포 독립성의 오류</strong>
이점2. 시스템을 독립적으로 개발하고, 배포 가능한 수십/수백/수천 개의 서비스들을 이용해 만들 수 있다고 믿는다.</p>
<p>그러나 </p>
<ol>
<li>서비스 기반이 확장 가능한 시스템을 구축하는 유일한 선택지가 아니다.</li>
<li>‘결합 분리 오류&#39;에 따르면 서비스라고 해서 항상 독립적으로 개발, 배포, 운영할 수 있는 것은 아니다.
<br><br></li>
</ol>
<h3 id="야옹이-문제">야옹이 문제</h3>
<hr>
<p>‘결합 분리 오류&#39;, ‘개발 및 배포 독립성의 오류’에 대한 예
<img src="https://velog.velcdn.com/images/cho-boori/post/a5a28b8a-e7ca-46d7-ba2c-71c5fd10c308/image.png" alt=""></p>
<blockquote>
<p>TaxiFinder: TaxiSupplier를 검토해 택시 후보 선별
TaxiSelector: 사용자의 요구 조건에 따라 후보 중 적합한 택시 선택
TaxiDispatcher: 해당 택시에 배차 지시
택시 통합 시스템이 각각의 서비스별로 나뉘어 개발, 운영되고 있다.</p>
</blockquote>
<p>만약 야옹이 배달 서비스를 추가하겠다고 한다면?</p>
<ul>
<li>서비스들이 모두 결합되어 있기 때문에 전부 변경해야하는 문제 발생</li>
<li>독립적으로 개발, 배포, 유지될 수 없다.</li>
</ul>
<p>→ 모든 소프트웨어의 횡단 관심사가 지닌 문제</p>
<ul>
<li>횡단 관심사란? 하나의 기능 자체에 공통적으로 들어가는 로직
  <strong>왜 여기서 횡단 관심사 문제가 발생했을까? (개인적인 생각)</strong>
  : 택시 서비스, 야옹이 배달 서비스 둘의 공통 로직을 구현하고, 변경할 때 서비스 전부를 변경해야하기 때문에</li>
</ul>
<p><br><br></p>
<h3 id="객체가-구출하다">객체가 구출하다</h3>
<hr>
<p>컴포넌트 기반 아키텍처에서 이 문제를 해결한다면?
<img src="https://velog.velcdn.com/images/cho-boori/post/54220343-127e-4181-93bb-e58b746d37dc/image.png" alt=""></p>
<blockquote>
<p>배차에 특화된 로직 부분은 Rides 컴포넌트로 추출, 야옹이의 신규 기능은 Kittens 컴포넌트에 들어감
두 컴포넌트 모두 의존성 규칙 준수</p>
</blockquote>
<ul>
<li>다형적으로 확장할 수 있는 클래스 집합을 생성해 새로운 야옹이 문제를 처리했다.</li>
<li>야옹이 기능은 결합이 분리되며, 독립적으로 개발하여 배포할 수 있다.<br>
### 컴포넌트 기반 서비스
</li>
</ul>
<hr>
<p>서비스도 객체 지향 방식처럼 해결할 수 있을까? 🙆🏻‍♀️</p>
<p>서비스 또한 SOLID 원칙대로 설계할 수 있으며 컴포넌트 구조를 갖출 수도 있다.
<img src="https://velog.velcdn.com/images/cho-boori/post/933d9e64-9fb7-41a8-843b-6ed32ecab029/image.png" alt=""></p>
<ul>
<li>서비스 내부는 자신만의 컴포넌트 설계로 되어 있어, 파생 클래스를 만들어 신규 기능을 추가할 수 있다.
  → 변경에는 닫혀 있고, 확장에는 열려있는 ‘개방 폐쇄 원칙&#39; 준수</li>
</ul>
<br>

<h3 id="횡단-관심사">횡단 관심사</h3>
<hr>
<p><img src="https://velog.velcdn.com/images/cho-boori/post/ac6a3923-04a0-45e8-b4ab-43fa1dd46bf3/image.png" alt="">
횡단 관심사를 처리하려면, 서비스 내부는 의존성 규칙도 준수하는 컴포넌트 아키텍처로 설계해야 한다.</p>
<p>→ 아키텍처 경계를 정의하는 것은 서비스가 아닌, 서비스 내 위치한 컴포넌트다.
<br></p>
<h3 id="결론">결론</h3>
<hr>
<p>서비스 자체로는 아키텍처적으로 중요한 요소는 아니다.</p>
<p>서비스를 단일 컴포넌트로 만들거나, 다수의 컴포넌트로 구성되는 컴포넌트 기반 서비스를 만들어야 한다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[#2 자바스크립트란?]]></title>
            <link>https://velog.io/@cho-boori/JS-Deep-Dive-2-%EC%9E%90%EB%B0%94%EC%8A%A4%ED%81%AC%EB%A6%BD%ED%8A%B8%EB%9E%80</link>
            <guid>https://velog.io/@cho-boori/JS-Deep-Dive-2-%EC%9E%90%EB%B0%94%EC%8A%A4%ED%81%AC%EB%A6%BD%ED%8A%B8%EB%9E%80</guid>
            <pubDate>Wed, 03 Aug 2022 12:52:57 GMT</pubDate>
            <description><![CDATA[<h3 id="자바스크립트-성장의-역사">자바스크립트 성장의 역사</h3>
<ul>
<li>초창기 자바스크립트는 웹페이지의 보조적인 기능을 수행하기 위해 한정적인 용도로 사용되었다. 대부분 로직은 웹서버에서 실행되었고, 브라우저는 HTML, CSS를 단순히 렌더링하는 수준이었다.</li>
</ul>
<ol>
<li>Ajax<ul>
<li>서버와 브라우저가 비동기 방식으로 데이터를 교환할 수 있는 통신 기능</li>
<li>🚨 변경이 필요 없는 부분까지 처음부터 다시 렌더링해야하는 문제가 있었는데,
Ajax가 등장함으로써, 변경되어야 하는 부분만 다시 렌더링하도록 하는 방식</li>
</ul>
</li>
<li>jQuery<ul>
<li>번거롭던 DOM을 더욱 쉽게 제어할 수 있게 되었다.</li>
</ul>
</li>
<li>V8 자바스크립트 엔진<ul>
<li>빠르게 동작하는 자바스크립트 엔진의 필요성이 대두되면서 등장했다.</li>
<li>V8 자바스크립트 엔진으로 시작된 JS의 발전으로 과거 웹서버에서 수행되던 로직들이 대거 클라이언트로 이동했고, 프런트엔드 영역이 주목받는 계기가 되었다.</li>
</ul>
</li>
<li>Node.js<ul>
<li>V8 자바스크립트 엔진으로 빌드된 자바스크립트 런타임 환경이다.</li>
<li>브라우저의 자바스크립트 엔진에서만 동작하던 자바스크립트를, 브라우저 이외의 환경에서도 동작할 수 있도록 독립시킨 JS 실행 환경이다.</li>
<li>자바스크립트는 크로스 플랫폼을 위한 중요 언어로 주목받고 있다.<ul>
<li>크로스 플랫폼: 크로스 + 플랫폼 ⇒ 다양한 플랫폼에서 사용할 수 있는 언어 (Window, mac, Linux 등)</li>
</ul>
</li>
</ul>
</li>
<li>SPA 프레임워크<ul>
<li>Single Page Application이란 뜻</li>
<li>한개의 페이지로 구성되어 있으며, 서버에 요청이 있을 때마다 신규페이지를 불러와 그리는 MPA 방식이 아닌 Client 상에서 Rendering 이루어지는 방식으로 동작</li>
<li>CBD 방법론 기반 (Component based development)</li>
</ul>
</li>
</ol>
<h3 id="자바스크립트의-특징">자바스크립트의 특징</h3>
<ul>
<li><p>웹 브라우저에서 동작하는 유일한 프로그래밍 언어</p>
</li>
<li><p>개발자가 별도의 컴파일 작업을 수행하지 않는 인터프리터 언어</p>
</li>
<li><p>대부분 모던 자바스크립트 엔진이 인터프리터+컴파일러를 결합해 느린 인터프리터의 단점을 해결했다.</p>
</li>
<li><p>런타임에 컴파일되며, 실행 파일이 생성되지 않고 인터프리터 도움 없이 실행할 수 없기 때문에 컴파일러 언어라고는 할 수 없다.</p>
</li>
<li><p>명령형, 함수형, 객체지향 프로그래밍(프로토타입 기반/클래스 기반 x) 지원하는 멀티 패러다임 프로그래밍 언어이다.</p>
<p>➕ 익스폴로러/구형 브라우저 고려해야한다면 바벨과 같은 트랜스파일러를 사용해 소스코드를 다운그레이드 해야한다.</p>
</li>
</ul>
]]></description>
        </item>
    </channel>
</rss>