- HTML 또는 XML 문서의 계층구조와 정보를 표현하며, 이를 제어할 수 있는 프로퍼티와 메서드를 제공하는 트리 자료구조다.
브라우저는 웹 문서(HTML, XML 등)를 로드한 후, 파싱하여 DOM을 생성한다.

html 문서를 구성하는 각 요소와 요소의 어트리뷰트, 텍스트를 각각의 객체로 만들고 이들 객체를 부자 관계를 표현할 수 있는 트리 구조로 구성한다.

노드 트리의 각 노드는 html의 요소를 나타낸다.
DOM은 자바스크립트를 통해 동적으로 변경될 수 있고, 변경된 DOM은 렌더링에 반영된다. (html을 직접 변경X)

01. getElementById(id)
02. querySelector(cssSelector)
태그? 요소?
태그(tag) : 단순히 < 와 >로 묶인 명령어들을 의미
ex)
<p>요소(element) : 태그들을 이용해서 만들어낸 웹페이지의 구성요소, 내용을 포함해 시작태그와 종료태그까지를 엘리먼트
ex)
<p>이것은 문단입니다.</p>

HTML Collection

getElementsByClassName(class),
getElementsByTagName(tagName) 메서드가 반환하는 객체
예시 )
<body>
<div>
<ul>
<li id="one" class="red">1</li>
<li id="two" class="red">2</li>
<li id="three" class="red">3</li>
</ul>
</div>
</body>
<script>
const elems = document.getElementsByClassName('red');
for (let i = 0; i < elems.length; i++) {
// 클래스 어트리뷰트의 값을 변경한다.
elems[i].className = 'blue';
}
</script>

3번의 loop )
i = 0, elems의 첫 요소(li#one.red)의 class 값이 blue로 변경.
elems는 실시간으로 Node의 상태 변경을 반영.
elems의 첫 요소는 li#one.blue로 변경되었으므로 선택 조건(‘red’)에 해당되지않아 실시간으로 제외된다.
i= 1, 첫째 요소는 제거되었으므로 elems[1]은 3번째 요소(li#three.red)가 된다. li#three.blue로 변경되고 마찬가지로 HTMLCollection에서 제외된다.
i= 2, 1,3번째 요소가 제거되었으므로 2번째 요소(li#two.red)만 남았으나, 현재 elems.length는 1이므로 반복을 종료한다. 따라서 elems에 남아 있는 2번째 li 요소(li#two.red)의 class 값은 변경되지 않는다.
NodeList

querySelectorAll 메서드가 반환하는 객체
DOM을 변경할 경우
리플로우? 리페인트?
JS 코드에 DOM이나 CSSOM가 API를 통해 변경된 경우, 변경된 DOM, CSSOM은 다시 렌더 트리로 결합되고 다시 레이아웃과 페인트 과정을 거쳐 브라우저 화면에 렌더링 된다.
const start = Date.now();
console.log("Page load took " + (Date.now() - start) + "milliseconds");
Element.innerHTML (프로퍼티)
요소 노드의 시작태그와 종료태그 사이 내 포함된 모든 HTML 마크업을 문자열로 반환한다.
const app = document.querySelector('#app');
for (let i = 0; i < 1000; i++) {
app.innerHTML += '<div>Hello<div>';
}
const app = document.querySelector('#app');
let template = ''
for (let i = 0; i < 1000; i++) {
template += '<div>Hello<div>';
}
app.innerHTML = template;
Element.insertAdjacentHTML(position, DOMString)
<position의 종류>

const app = document.querySelector('#app');
for (let i = 0; i < 1000; i++) {
app.insertAdjacentHTML('beforeend', '<div>Hello<div>');
}
// Page load took 13ms
const app = document.querySelector('#app');
let template = '';
for (let i = 0; i <1000; i++) {
template += '<div>Hello<div>';
}
app.insertAdjacentHTML('beforeend', template);
// Page load took 30ms
Document.createElement(tagName)
Node.appendChild(childNode)
const app = document.querySelector('#app');
for (let i = 0; i < 1000; i++) {
const li = document.createElement('li');
app.appendChild(li);
}
const app = document.querySelector('#app');
// 컨테이너 요소 노드 생성
const container = document.createElement('div');
for (let i = 0; i < 1000; i++) {
const li = document.createElement('li');
container.appendChild(li);
}
app.appendChild(container);
DocumentFragment
function addElements() {
const app = document.querySelector('#app');
//DocumentFragment 노드 생성
const docFrag = document.createDocumentFragment();
for (let i = 0; i < 1000; i++) {
const li = document.createElement('li');
docFrag.appendChild(li);
}
app.appendChild(docFrag);
}
참조
https://poiemaweb.com/js-dom
https://www.youtube.com/watch?v=q1fQnGG1bgU
민정님 오늘 강의에서 DOM 부분 듣다가 스터디 복습하고 싶어져서 찾아왔습니다ㅎㅎㅎ 오늘 강의에서 나왔던 createFragment까지 정리되어 있어서 좋아용👍