-
[해결] cloneNode 사용 레퍼런스 문제카테고리 없음 2021. 12. 7. 12:06
배열에 있는 값을 하나씩 출력하려 했지만 첫번째 칸은 빈칸이고 진짜 원하는 값은 다음 리스트로 밀렸다 <!DOCTYPE html> <html> <head> <title>DOM Review</title> <meta charset="UTF-8" /> </head> <body> <div id="app"> <ul class="city-list"> </ul> </div> TODO: DOM을 이용하여 places 배열의 모든 요소를 화면에 렌더링합니다. <script> const places = [ { id: 1, city: "Biloxi", country: "United States", address: "Walton" }, { id: 2, city: "Carmen de Viboral", country: "Colombia", address: "Drewry" }, { id: 3, city: "New Mīrpur", country: "Pakistan", address: "Morningstar" }, { id: 4, city: "Seropédica", country: "Brazil", address: "Parkside" }, { id: 5, city: "Ponjen", country: "Indonesia", address: "Gina" } ]; const cityList = document.querySelector(".city-list") const container = document.createElement("li") let country = document.createElement("span") country.classList.add("country") let city = document.createElement("span") city.classList.add("city") let address = document.createElement("span") address.classList.add("address") const cityAndAddress = document.createElement("div") cityAndAddress.append(city) cityAndAddress.append(address) container.append(country) container.append(cityAndAddress) places.map(place => { const cloneContainer = container.cloneNode(true); cloneContainer.setAttribute("key", place.id); country.textContent = place.country city.textContent = place.city address.textContent = place.address cityList.append(cloneContainer) }) </script> </body> </html>
핵심만 보면 이렇다.
cityAndAddress.append(city) cityAndAddress.append(address) container.append(country) container.append(cityAndAddress) places.map(place => { const cloneContainer = container.cloneNode(true); cloneContainer.setAttribute("key", place.id); country.textContent = place.country city.textContent = place.city address.textContent = place.address cityList.append(cloneContainer) })
이부분에서 cloneNode의 위치가 문제이다.
cloneNode는 깊은 복사를 하기때문에 container에 append되어있던 country를 수정하는 것으로는
cloneNode에 append되어있는 country의 복제는 수정되지않는다.
처음에 textcontent를 넣어주지 않아서 비어있는 상태인 엘리먼트들이 append되어있는 container를 cloneNode로 복제한 것이니
cloneContainer에 들어있는 엘리먼트(.i.g country, cutyAndAddress)들은 비어있는 상태이다.
복제한 후에 textContent의 값을 재할당하려 시도해봤자 container에 있는 애들의 값을 바꿨을 뿐이다.
그 상태로 cityList에 cloneContainer를 했으니
처음 루프에선 비어있는 값이 나온것이다.
그 다음루프에서는 전 루프에서 재할당했던 값이 들어있는 container를 복제했으니 값이 한번씩 밀린것이다.
places.map(place => { country.textContent = place.country city.textContent = place.city address.textContent = place.address const cloneContainer = container.cloneNode(true); cloneContainer.setAttribute("key", place.id); cityList.append(cloneContainer) })
수정하고 난 후.
원하던 대로 출력이 된다.
Ref:
[JavaScript] 얕은 복사(Shallow Copy)와 깊은 복사(Deep Copy)
깂은 복사와 얕은 복사에 대해 알아보겠다. 이 글의 초반 내용은 이전 포스팅의 (원시 타입과 참조 타입의 차이과 맥락이 비슷하며, 위 포스팅은 원시 타입과 참조 타입의 차이점이라면 아래는
velog.io