타이머(setTimeout, setInterval) 제대로 쓰기

작업 중 타이머 기능을 구현하기 위해 setTimeout을 사용하게 되었고, 이와 관련된 개념과 React에서의 활용법을 정리했습니다.

4/25/2025

javascript

조회수 1

JavaScript 호출 스케줄링 정리

호출 스케줄링은 특정 시간이 지난 후에 함수를 실행하도록 예약하는 것을 의미합니다.

JavaScript에서는 대표적으로 두 가지 방법을 제공합니다.

  • setTimeout: 일정 시간 후 한 번 실행

  • setInterval: 일정 시간마다 반복 실행

1. setTimeout

setTimeout은 지정된 시간이 지난 후 함수를 한 번만 실행합니다.

  • 첫 번째 인자: 실행할 함수

  • 두 번째 인자: 지연 시간(ms)

기본 사용법

// 3초 후에 메시지 출력
setTimeout(() => {
  console.log('3초가 지남');
}, 3000);

타이머 취소하기

clearTimeout을 사용하면 예약된 함수가 실행되기 전에 취소할 수 있습니다.

const timer = setTimeout(() => {
  console.log('이 메시지는 출력되지 않음');
}, 5000);

// 타이머 취소
clearTimeout(timer);

실용 예제: 디바운싱

사용자가 입력을 멈춘 후 0.5초 뒤에 검색을 실행하는 예제입니다.

let searchTimer;

function handleSearch(keyword) {
  clearTimeout(searchTimer);

  searchTimer = setTimeout(() => {
    console.log(`검색 실행: ${keyword}`);
    // API 호출 등의 검색 로직
  }, 500);
}

handleSearch('버블');
handleSearch('버블콘'); // 이것만 500ms 후 실행됨

2. setInterval

setInterval은 일정한 시간 간격마다 함수를 반복해서 실행합니다.

clearInterval로 중단하기 전까지 계속 실행됩니다.

기본 사용법

let count = 0;

const timer = setInterval(() => {
  count++;
  console.log(`${count}초 경과`);
}, 1000);

타이머 중지하기

let count = 0;

const timer = setInterval(() => {
  count++;
  console.log(`${count}초 경과`);

  if (count >= 5) {
    clearInterval(timer);
    console.log('인터벌 종료');
  }
}, 1000);

실용 예제: 시계

function displayClock() {
  const now = new Date();
  const hours = String(now.getHours()).padStart(2, '0');
  const minutes = String(now.getMinutes()).padStart(2, '0');
  const seconds = String(now.getSeconds()).padStart(2, '0');

  console.log(`${hours}:${minutes}:${seconds}`);
}

const clockTimer = setInterval(displayClock, 1000);

displayClock();

3. 중첩 setTimeout

3-1. setInterval의 문제점

setInterval은 함수 실행 시간을 고려하지 않고 일정한 간격으로 함수를 호출합니다.

setInterval(() => {
  // 이 작업이 2초 걸린다면?
  heavyTask(); // 2초 소요
}, 1000); // 1초마다 실행 요청
  • 함수가 끝나기 전에 다음 인터벌이 실행될 수 있습니다.

  • 비동기 작업에서는 중복 실행 문제가 생기기 쉽습니다.

3-2. 중첩 setTimeout의 장점

중첩 setTimeout은 함수 실행이 끝난 후 다음 실행을 예약할 수 있습니다.

function repeatTask() {
  console.log('작업 실행');

  setTimeout(repeatTask, 1000);
}

setTimeout(repeatTask, 1000);

예제: 에러 발생 시 재시도 간격 늘리기

let delay = 1000;

function fetchData() {
  const success = Math.random() > 0.3;

  if (success) {
    delay = 1000;
    setTimeout(fetchData, delay);
  } else {
    delay *= 2;

    if (delay > 16000) {
      delay = 16000;
    }

    setTimeout(fetchData, delay);
  }
}

fetchData();

3-3. setInterval vs 중첩 setTimeout

setInterval

시작 → [1초] → 함수 실행(2초 소요) → 함수 실행(중복) → ...
  • 함수 실행 시간과 관계없이 일정 간격으로 호출됩니다.

  • 함수가 끝나지 않아도 다음 호출이 쌓일 수 있습니다.

중첩 setTimeout

시작 → [1초] → 함수 실행(2초 소요) → [1초] → 함수 실행 → ...
  • 함수가 완전히 끝난 후 다음 실행을 예약합니다.

  • 중복 실행을 방지하기 쉽습니다.

비교 항목 setInterval 중첩 setTimeout
호출 간격 무조건 일정 실행 완료 후 대기
실행 시간 보장 보장 안 됨 보장됨
안정성 낮음 높음
중복 실행 위험 있음 없음
유연성 고정 간격만 가능 동적으로 간격 조절 가능
사용 추천 단순 반복 작업 비동기/무거운 작업

3-4. 언제 무엇을 사용해야 하나?

setTimeout 사용

  • 일회성 지연 실행

  • 디바운싱/쓰로틀링

  • 조건부 반복

  • 비동기 작업 반복

setInterval 사용

  • 매우 가벼운 작업의 단순 반복

  • 정확한 시간 간격이 중요한 애니메이션

  • 실시간 시계/카운터

중첩 setTimeout 사용

  • 서버 요청 같은 비동기 작업 반복

  • 실행 시간이 불규칙한 작업

  • 에러 시 재시도 로직

  • 실행 간격을 동적으로 조절해야 할 때

4. 참고

setTimeout(0)은 정확히 0초 뒤에 실행된다는 의미가 아닙니다.

  • 타이머 콜백은 현재 실행 중인 작업이 끝난 뒤 이벤트 루프를 통해 실행됩니다.

  • 브라우저는 중첩 타이머가 과도하게 CPU를 점유하지 않도록 최소 지연 시간을 둘 수 있습니다.

  • HTML 표준에서는 중첩 타이머에 대해 최소 4ms 지연이 적용될 수 있음을 설명합니다.

참고 문서: HTML Standard - Timers

댓글 0