자바스크립트 성능 향상의 키 #1 - DocumentFragment

2011/08/09 11:30



웹 페이지 상에서 자바스크립트 성능 향상을 위한 방법을 몇가지를 연재물로 공유해 보도록 하겠습니다.

자바스크립트로 DOM 객체를 생성하고 핸들링 할 때, 간단히 성능을 높이는 방법으로 DocumentFragment 를 쓰는 방법이 있습니다.

DocumentFragment  가 무엇이고 왜 속도가 올라가는지, 어떻게 사용하는지에 대해 알려드리겠습니다.

 

먼저, DocumentFragment 란.. 웹 페이지에 객체를 생성할 때 생성 객체를 Body 에 넣기 전에 미리 만들어 두는 것을 말합니다.

그럼 어디서 성능 향상 포인트가 발생하는지 알아보겠습니다.

 

웹브라우져는 웹페이지 내부의 View 영역 안에 보이는 객체에 변화가 생길 때 reflow 를 하게 됩니다.

 

re·flow

명사[U], (전문 용어)

1.리플로 납땜, 리플로 연납접(땜납을 녹여 금속을 이어붙이는 것)
2.리플로(컴퓨터 화면에서 텍스트가 차지하는 공간을 조정하는 것)

 

reflow란, 뷰 영역을 재조정 하는 프로세스인데, 한 객체의 크기가 변경될 경우 다른 여러 객체들의 크기도 함께 영향 받을 수 있습니다. 이런 것들을 재조정 하는 과정이라고 보시면 됩니다. 예를들어 텍스트 글자가 길어져서 다음 라인으로 넘어가니, 그걸 담는 박스 높이도 길어지고.. 아래 있는 객체를 밀어내고 하는 등등.. 하나의 객체만 움직여도 수많은 다른 객체들이 영향 받을 수 있고.. 그 객체들이 영향 받을 때에도 또다시 reflow 가 발생해서 사이드이팩트가 꽤 크게 발생하기도 합니다.

 

이 reflow 를 최소화 함으로써 얻을 수 있는 성능 향상 방법으로 DocumentFragment 를 사용 할 수 있습니다.

 

만약 DIV 객체를 1 개 생성하고 그 안에 A 태그 객체를 1000 개 생성한다고 합시다.

 

1. Div 생성

2. Body 에 Div 넣기

3. A 생성

4. Div 에 A 넣기*1000

 

이걸 스크립트로 하면 다음과 같습니다. (시간측정도 포함 했습니다)

[Result] 눌러서 동작을 확인해보세요. 안보이시면 - http://jsfiddle.net/hbsto/EM5cs/



다음은 DocumentFragment 를 사용해 보겠습니다.

 

1. Div 생성

2. A 생성

3. Div에 A넣기*1000

4. Body 에 Div 넣기

 

이걸 스크립트로 하면 다음과 같습니다.

http://jsfiddle.net/hbsto/Uvzp5/

    

IE9 기준으로 첫번째는 575ms, 두번째는 514ms 가 나왔습니다.

엄청 간단한 방법으로, 이렇게 단순한 구조의 DOM 에서도 10% 가까운 향상을 확인 할 수 있습니다.

 

달라진 점은 Body 에 Div 가 들어가는 타이밍 뿐입니다.

첫번째에서 Div 는 시작과 함께 Body 에 들어가서 매번 A 를 추가 했습니다.

두번째는 Div 를 먼저 만들어 놓고 A를 추가한 후 맨 마지막에 Body 에 추가 했습니다.

 

첫번째는 reflow 가 1001 번 일어나게 됩니다.

두번째는 reflow 가 1번 일어나게 됩니다.

아직 Body 안에 들어가지 않은 객체는 단지 메모리에 생성된 아주 가벼운 형태로 존재하며, 이 상태에서 자식을 추가하는 행위는 View 영역에 아무런 영향을 주지 않게 되어 reflow 가 발생하지 않습니다.

 

이 성능 향상 방법은 웹 페이지 내의 객체가 복잡하게 구성되어 있고 CSS 가 다양할수록 효과가 커집니다.

객체를 실시간 생성할 때에는 Container 에 해당하는 부모 객체를 가장 마지막에 DOM Tree 에 넣어 주는 것이 유리합니다~_~


CCL

출처 - http://blog.naver.com/PostView.nhn?blogId=bitofsky&logNo=50117823005&categoryNo=0&parentCategoryNo=0&viewDate=&currentPage=8&postListTopCurrentPage=1&userTopListOpen=true&userTopListCount=5&userTopListManageOpen=false&userTopListCurrentPage=8






JavaScript 최적화: DOM 핸들링 속도 개선

JavaScript 최적화: DOM 핸들링 속도 개선

들어가기 전에

자바스크립트는 오늘날 웹 서비스 개발에서 뗄레야 뗄 수 없는 언어이다. 자바스크립트를 통하여 누구나 손쉽게 문서 객체 모델 (Document Object Model이하 DOM)을 자유롭게 조작하여 역동적인 웹 페이지를 만들 수 있다. 이렇게 대부분의 웹 사이트에서 사용하고 있는 스크립트를 사용한 DOM의 조작 기능에는 성능상의 문제가 있다. 이 글에서는 스크립트를 사용한 DOM 조작 시 발생하는 성능저하 문제점과 그 최적화에 대해 알아본다.

 

DOM의 빠른 갱신 시 발생하는 성능 문제

낮은 버전의 브라우저 특히 IE 에서는 스크립트를 사용하여 DOM을 빠르게 갱신하는 경우 심각한 성능저하를 발생시킨다. 아직까지 각 사이트에서 많이 사용되는 IE7을 기준으로 예제를 작성하였다.

< 예제1> 테이블 병합

이 스크립트는 테이블을 읽어 첫번째 열을 2개씩 묶어 병합하는 스크립트 코드이다. 위 예제를 통해 IE7에서의 성능저하를 체감하기 위해서는 CSS 적용이 필요하다. 눈에 띄는 결과를 보여줄 수 있는 테스트를 위해 2개의 열과 1000개의 행을 가진 테이블을 준비하였으며 아래와 같은 CSS를 설정하였다.

td, th{font-size: 13px;border: 1px solid black;}
th{background-color: #000000; height:40px;color: white;}
td{background-color: #EEEEEE; height:20px;color: black;}
table{border: 1px solid black;border-collapse:collapse;}

<예제1-1> 예제 CSS

브라우저병합 소요시간(초)
IE 78.852s
IE 80.224s
IE 90.217s
Fire Fox (25)0.010s
Chrome (30)0.014s

<표1> 테이블 병합 스크립트[예제1] 브라우저 별 소요시간

위 예제의 결과로 IE7에서의 큰 성능저하를 볼 수 있다. 먼저 원인을 짚고 넘어가보자. 성능 저하의 원인은 스크립트가 DOM을 수정함으로써 생기는 리플로우(reflow)에 있다. 리플로우란 브라우저가 DOM요소들을 다시 렌더링하는 과정을 말하는데 최신 브라우저는 DOM이 빠르게 갱신될 때 과도한 렌더링으로 인한 소요시간 증가를 막아주지만 IE7은 그렇지 않다. 예제에서는 500번의 열 크기 변환과 500번의 열 삭제 총 1000번의 리플로우가 있었다. 이러한 많은양의 리플로우가 발생하는 경우 브라우저는 큰 성능저하를 보여주며 웹 페이지의 DOM이 복잡하게 구성되어 있고 CSS가 많이 적용된 사이트일수록 더욱 심해진다.

이 문제의 해결책은 바로 DocumentFragment를 사용하는 것이다. DocumentFragment는 화면상에 표시되지 않는 document-like한 컨테이너로 DOM이 갱신될 때 마다 과도한 리플로우를 하지 않도록 한다

<예제2>DocumentFragment를 사용한 리플로우를 최소화 한 DOM 갱신

 

브라우저병합 소요시간(초)
IE 73.647s
IE 80.166s
IE 90.044s
Fire Fox (25)0.008s
Chrome (30)0.006s

<표2> – 브라우저 별 병합 스크립트 소요시간 2

1000회의 리플로우 횟수를 2회로 줄인 결과 예제 스크립트는 IE7에서 기존 코드 대비 약 3배의 성능향상이 있었다. 다른 브라우저도 컴퓨터 성능에 따라 약간씩 다르지만 평균적으로 2배의 성능향상을 보여준다. IE에서 가장 성능저하가 매우 심한 테이블로 예제를 작성하였으나 리플로우를 줄임으로써 얻는 최적화 방식은 IE만이 아닌 모든 브라우저에서 스크립트로 DOM을 조작하는 모든 영역에서 활용할 수 있는 방식임을 예제를 통해 알 수 있다.

DocumentFragment는 본래 용도인 생성에도 빠른 성능을 보여준다.

<예제3-1> appendChild를 사용한 DOM 그리기

 

<예제3-2> documentFragment를 사용한 DOM 그리기

브라우저예제3-1 소요시간(초)예제3-2 소요시간(초)
IE 70.201s0.080s
IE 80.104s0.030s
IE 90.044s0.020s
Fire Fox (25)0.005s0.002s
Chrome (30)0.003s0.000s

<표2> 브라우저별 DOM 그리기 소요시간

단순한 DOM 변경에도 평균적으로 2배의 성능향상이 있었다.

마치며

DocumentFragment을 사용한 DOM 조작 스크립트 최적화 방법은 웹 개발에서 흔하게 무시되곤 하는 영역이다. 최신 브라우저의 경우 리플로우가 발생하지 않도록 최적화되고 성능이 향상되어 그 차이가 체감되지 않기 때문이다. 그러나 ActiveX 기반의 국내 웹 환경상 낮은 버전의 IE를 요구하는 경우가 분명히 존재하며 그런 환경이 아니더라도 많은 DOM을 조작해야만 하는 역동적인 화면에서의 브라우저의 부담을 덜어주고 빠른 화면갱신을 위해서 DocumentFragment를 활용하면 충분한 최적화를 얻을 수 있을 것이다.

 

브라우저별 DocumentFragment 사용과 미사용 성능차이

chart



출처 - http://www.nextree.co.kr/p2081/







'Development > JavaScript' 카테고리의 다른 글

javascript - iife setTimeout  (0) 2014.04.01
javascript - window.JSON 객체  (0) 2014.03.27
javascript - requirejs와 AMD  (0) 2014.01.19
javascript - CommonJS와 AMD  (0) 2014.01.19
javascript - url link 자동 인식(autoLink) 처리  (0) 2014.01.08
Posted by linuxism
,