LogoSEO Jing
  • All Posts
  • SEO Jing
  • okayJing
  • KD Team
  • CLab CoreTeam
  • Study

Contact Me

© 2026 SEOJing. All rights reserved.

프론트엔드스터디JavaScript스코프DOM이벤트버블링

사전 진단 퀴즈 3단계 (변수와 DOM)

2026년 3월 19일·11분 읽기

본격적인 웹 개발을 한다면 자바스크립트부터

1단계와 2단계에서 마크업과 스타일링의 기본기를 다졌다면, 3단계에서는 웹 개발의 꽃 자바스크립트의 근본적인 동작 원리를 점검합니다.

자바스크립트는 매우 유연하고 쉽다는 인식이 있는 언어이지만, 스코프(Scope), 참조(Reference), 이벤트 흐름(Event Flow)의 원리를 정확히 알지 못하면 원인을 알 수 없는 버그에 시달리게 됩니다. 특히 이 단계의 지식들은 추후 리액트의 상태 관리와 렌더링 최적화를 이해하기 위한 필수적인 개념이에요.


질문 1. 변수 스코프 (Scope)

질문 의도

자바스크립트에서 변수가 살아있는 유효 범위(Scope)를 정확히 이해하고 있는지 확인합니다. "var는 사용하지 마라"라는 말을 자바스크립트를 공부해본 사람들이라면 자주 들어보셨을텐데요. 왜 쓰지 말라는거지? 하는 의문이 들었나에 대해 물어보는 질문입니다. var, let, const의 차이를 아는 것은, 의도치 않은 변수 덮어쓰기나 메모리 누수를 방지하기 위한 가장 기본적인 소양이며, 더 나아가 공부할 때 어느 정도의 깊이를 가지고 공부하는지 알아볼 수 있는 대목입니다.

문제

for 반복문 안에서 쓸 임시 변수를 선언하려고 합니다. 요즘은 let을 주로 사용하는데요. 만약 실수로 반복문 블록 중괄호 밖에서 이 변수를 부르려고(console.log) 할 때, var와 let은 각각 어떤 결과를 보여줄까요?

정답 및 풀이

  • 정답: let으로 선언한 변수는 참조 에러(ReferenceError)를 발생시키지만, var로 선언한 변수는 반복문이 끝난 후의 최종 숫자를 정상적으로 출력합니다.
  • 풀이 과정: let은 '블록 레벨 스코프'를 가지므로 중괄호 안에서만 존재하고 밖에서는 소멸합니다. 반면 var는 '함수 레벨 스코프'를 가지기 때문에, 함수 내부가 아니라면 단순한 제어문이나 반복문의 블록을 무시하고 전역 혹은 상위 스코프로 새어나가게 됩니다.
javascript
for (var i = 0; i < 3; i++) {}
console.log(i); // 3 출력 (변수가 밖으로 새어나옴)

for (let j = 0; j < 3; j++) {}
console.log(j); // ReferenceError: j is not defined (안전하게 보호됨)

관련 개념 설명

  • 블록 레벨 스코프: 중괄호로 감싸진 코드 블록 내부에서만 변수가 유효합니다.
  • 함수 레벨 스코프: 함수의 코드 블록 내부에서만 변수가 유효합니다.
  • 팁: var는 예기치 못한 곳에서 변수 값이 변경되는 사이드 이펙트를 유발하므로, 현대 프론트엔드 개발에서는 절대 사용하지 않는 것이 원칙입니다. 기본적으로 const를 사용하고, 재할당이 꼭 필요한 경우에만 제한적으로 let을 사용합니다.

포스트 목록

/study/clab-26-1/preclass
파일 5개, 폴더 0개
사전 진단 퀴즈 1단계 (HTML/CSS)사전 진단 퀴즈 2단계 (HTML/CSS 활용)사전 진단 퀴즈 3단계 (변수와 DOM)사전 진단 퀴즈 4단계 (배열, 함수, 비동기)사전 진단 퀴즈 5단계 (선언적 UI와 상태)

질문 2. 데이터 타입과 참조 (Reference)

질문 의도

자바스크립트 메모리 할당 방식의 핵심인 원시 타입과 참조 타입의 차이를 묻습니다. 이 개념을 모르면 앞으로 배울 스프레드 문법이나, 구조 분해를 이해하지 못하는데요. 특히 리액트에서 상태(State)의 불변성(Immutability)을 지키기 위해 반드시 완벽하게 이해해야 하는 개념입니다.

문제

사용자 정보 객체 userA를 만들고, const userB = userA; 형태로 복사했습니다. 이후 userB의 이름을 바꿨더니 원본인 userA의 이름까지 바뀌어버렸습니다. 객체나 배열을 다룰 때 왜 이런 일이 발생하며, 어떻게 예방할 수 있을까요?

정답 및 풀이

  • 정답: 객체는 실제 값이 아닌 데이터가 저장된 메모리 주소를 참조하기 때문입니다. 이를 예방하려면 스프레드 연산자(...) 등을 사용하여 얕은 복사나 깊은 복사를 해야 합니다.
  • 풀이 과정: 숫자나 문자는 변수에 실제 값이 그대로 들어갑니다. 하지만 객체나 배열은 크기가 유동적이므로 메모리 어딘가에 저장해 두고 그 위치(주소)만 변수에 기록합니다. 따라서 할당 기호(=)로 복사하면 주소만 복사되므로, 결국 두 변수가 같은 원본 데이터를 바라보게 됩니다.
javascript
const userA = { name: "Kim" };

// 잘못된 복사 (주소만 복사됨)
const userB = userA;
userB.name = "Lee";
console.log(userA.name); // "Lee" (원본이 훼손됨)

// 올바른 복사 (새로운 객체를 만들어 값만 펼쳐 넣음)
const userC = { ...userA };

관련 개념 설명

  • 원시 타입(Primitive Type): String, Number, Boolean 등 값 자체가 저장되는 타입입니다.
  • 참조 타입(Reference Type): Object, Array, Function 등 메모리 주소가 저장되는 타입입니다.
  • 팁: 리액트에서는 상태 객체를 직접 수정(userA.name = "Lee")하면 화면이 리렌더링되지 않습니다. 반드시 새로운 객체를 만들어(복사) 교체해 주어야 합니다.

질문 3. DOM 탐색 API

질문 의도

바닐라 자바스크립트로 웹 요소를 제어할 때 가장 기본이 되는 DOM 선택자(Selector)의 활용 능력을 확인합니다. 사실 미묘한 성능 향상이 필요한 부분이 아니라면 qs(querySelector)를 주로 사용합니다.

문제

HTML에서 특정 요소를 찾으려 합니다. document.getElementById('alert')를 쓰는 것과 document.querySelector('#alert')를 쓰는 것은 결과는 같아 보이지만, 두 방식은 어떤 차이가 있고 언제 무엇을 쓰는 게 좋을까요?

정답 및 풀이

  • 정답: getElementById는 오직 ID 속성만 찾을 수 있으며 실행 속도가 미세하게 더 빠릅니다. querySelector는 CSS 선택자 문법을 모두 사용할 수 있어 유연성이 훨씬 뛰어납니다.
  • 풀이 과정: 과거에는 요소를 찾기 위해 getElementById나 getElementsByClassName 등을 목적에 따라 번갈아 사용해야 했습니다. 하지만 최신 자바스크립트에서는 CSS 문법을 그대로 활용해 복잡한 구조의 요소도 한 번에 찾을 수 있는 querySelector 하나로 통일하여 사용하는 추세입니다.
javascript
// ID로만 검색 가능
const box1 = document.getElementById("myBox");

// ID, Class, 자식 요소 등 CSS 선택자 모두 사용 가능
const box2 = document.querySelector("#myBox");
const activeItem = document.querySelector(".list .item.active");

관련 개념 설명

  • DOM (Document Object Model): HTML 문서를 자바스크립트가 이해할 수 있는 객체 형태로 트리화한 구조입니다.

질문 4. 이벤트 버블링 (Event Bubbling)

질문 의도

브라우저에서 이벤트가 발생했을 때 부모 요소로 전파되는 흐름을 제어할 수 있는지 확인합니다. 모달창(팝업창)이나 드롭다운 메뉴 밖을 클릭했을 때 창이 닫히게 만드는 UI 패턴을 구현하려면 반드시 알아야 하는 필수 개념입니다.

문제

모달창 바깥의 어두운 배경을 클릭했을 때 창이 닫히게 만들고 싶습니다. 배경을 클릭했는데 모달창 내부 요소의 클릭 이벤트까지 건드리지 않게 하려면(이벤트 흐름 제어) 어떻게 해야 할까요?

정답 및 풀이

  • 정답: 모달창 내부 요소에 클릭 이벤트를 달고 이벤트 객체의 stopPropagation() 메서드를 호출하여 부모로의 이벤트 전파를 막습니다. 또는 배경 요소의 이벤트에서 event.target과 event.currentTarget이 일치할 때만 닫히도록 조건문을 추가합니다.
  • 풀이 과정: HTML의 특정 요소를 클릭하면, 그 요소에만 이벤트가 발생하는 것이 아니라 그 요소를 감싸고 있는 모든 부모 요소들로 클릭 이벤트가 물방울(Bubble)처럼 번져 올라갑니다. 따라서 모달창 안의 버튼을 눌러도 부모인 배경까지 클릭된 것으로 간주되어 창이 닫혀버리는 문제가 발생합니다.
javascript
const modalBg = document.querySelector(".modal-background");
const modalContent = document.querySelector(".modal-content");

// 방법 1: 내부 요소에서 버블링 차단
modalContent.addEventListener("click", function (event) {
  event.stopPropagation(); // 부모인 modalBg로 클릭이 넘어가지 않음
});

// 방법 2: 클릭된 대상이 배경 본인일 때만 실행
modalBg.addEventListener("click", function (event) {
  if (event.target === event.currentTarget) {
    closeModal();

관련 개념 설명

  • 이벤트 버블링: 특정 화면 요소에서 이벤트가 발생했을 때, 해당 이벤트가 더 상위의 화면 요소들로 전달되어 가는 특성입니다.
  • event.target: 실제 이벤트가 발생한 가장 안쪽의 요소입니다.
  • event.currentTarget: 이벤트 리스너가 실제로 바인딩된 요소입니다.

참고 문헌 (Sources)

본 사전 진단 퀴즈의 기초 개념은 다음의 공식 문서를 참고하여 작성되었습니다.

  • MDN Web Docs: let과 const

  • MDN Web Docs: 자바스크립트의 데이터 타입

  • MDN Web Docs: querySelector

  • KO.JAVASCRIPT.INFO: 이벤트 버블링과 캡처링

}
});