Joonas' Note

Joonas' Note

블로그 포스트 읽는 시간 예측하기 본문

개발/Javascript

블로그 포스트 읽는 시간 예측하기

2024. 2. 7. 22:52 joonas

    배경

    미디엄 블로그를 보다보면 아래와 같이 예상 읽기 시간이 나온다.

    예전에 사람이 글을 읽는 데 걸리는 평균 시간을 알아본 적이 있다. WPM(Words per minute) 라고 부르는 단위도 있어서 이미 연구가 있었던 듯 하다.

    아래와 같이 여러 나라에 대해서 WPM을 계산한 연구도 있지만 한글은 빠져있다. 한글을 제외하면 평균적으로 190~200 WPM 정도의 속도이다.

     

    TimeToRead | Wolfram Function Repository

    Function Repository Resource:  TimeToRead

    resources.wolframcloud.com

    그래서 한글에 대한 WPM을 찾아보다가 120 정도라는 글을 찾았고 한글과 영문의 분포에 따라 적절히 계산하기로 했다.

    영어의 경우에는 평균 단어 길이가 4.7 이다. (참고) 한글까지 찾기는 귀찮아서 이 겂을 그대로 사용하기로 했다.

    혼자만의 가정을 세우고 아래와 같이 읽기 시간을 계산했다.

    • 영문과 한글의 비율에 맞게 WPM 을 계산하고, 문장 총 길이를 곱하여 소요시간(분)을 구한다.
    • 이미지는 자세히 보더라도 30초를 안 넘길 것 같아서 30초 * 이미지 장수
    • 수식은 일반 문장보다는 읽는 데 시간이 더 필요하므로 평균 글자 수만큼 가중치를 더 준다.

    코드

    아래 함수를 호출하면 해당 element 를 기준으로 예측 시간을 계산한다.

    /** returns reading time in seconds */
    function estimateReadingTime(element) {
      const AVG_WORD_LEN = 4.7;
      const sum = (a) => a.reduce((acc, cur) => acc + cur, 0);
      const calcWordPerMin = (text) => {
          const kor = text.replaceAll(/[^ㄱ-ㅎㅏ-ㅣ가-힣]/gi, '').length;
          const eng = text.replaceAll(/[^a-zA-Z]/gi, '').length;
          return (120 * kor + 238 * eng) / (kor + eng)
      };
      const WPM = calcWordPerMin(element.textContent);
      const codes = element.querySelectorAll('code');
      const images = element.querySelectorAll('img');
      const contentWords = element.textContent.split(/\s+/).length;
      const maths = element.querySelectorAll('.mjx-chtml');
      const mathsLength = Array.from(maths).map(e => e.textContent.replace(/[^a-zA-Z0-9]+/gi, ' ').split(/\s+/).filter(Boolean).length);
      const detectMinutes = (contentWords / WPM) + (sum(mathsLength) / WPM / AVG_WORD_LEN) + (images.length * 0.5);
      return Math.round(detectMinutes * 60);
    }

    결과

    위 코드를 블로그 스킨에 적용했고, 아래와 같이 동적으로 시간 표시를 추가하도록 했다.

     

    Comments