상세 컨텐츠

본문 제목

KBO 포스트시즌 - 정규 시즌 순위 시뮬레이션 방법

야구-칼럼/KBO 포스트시즌 제도

by 야구고물상 2023. 12. 3. 23:47

본문

반응형

시뮬레이션 전 팀별 승률 샘플 생성

 

1. 먼저 팀별 승률의 분포를 알 필요가 있습니다. 이는 KBO 홈페이지, 스탯티즈 등을 통해 충분히 알 수 있습니다. 하지만 실제 이 승률은 팀 간 재능의 차이와 그 외의 운 등이 합쳐져서 얻게 된 결과입니다. 그렇기에 이 운을 제거할 필요가 있습니다.

2. 먼저 팀간 승률의 가장 기본적인 재료는 피타고리안 기대 승률을 이용하기로 했습니다. 그렇다고 해도 이 피타고리안 기대 승률 또한 어느 정도 운의 영향을 뺄 수 없는 기록입니다. 아주 크게 보자면, 이 기록이 승률의 많은 부분을 설명할 수 있으니까요. 그렇기에 여기에서 운의 영향을 빼게 될 텐데, 이는 이항 분포를 통해 알 수 있습니다. 0.500이 기대되는 팀이 50 경기를 했을 때 언제나 25경기를 이기는 건 아니니까요. 실제로는 11.2% 정도의 확률로 25승을 기록할 겁니다. 그렇다면 다른 88.8% 정도는 승이 25승보다 많거나 적을 거라는 얘기죠. 이렇게 이항 분포에 의한 편차를 빼 줘야 팀의 실제 재능 편차를 얻을 수 있을 거라는 이야기입니다. 실제 재능 편차를 얻기 전에 다음을 생각해 봅시다.

$$var(total) = {v}^{2} = var(talent)+var(luck) = {t}^{2}+{l}^{2}$$
여기에서 $t$는 재능의 표준편차, $l$은 운의 표준편차를 의미합니다. 그리고 운의 표준편차 $l$은 이항분포에 의한 효과를 의미하니 다음과 같이 생각할 수 있을 겁니다. $$l = \sqrt{p(1-p)/n}$$
이는 사건이 일어날 확률 p와 시행 횟수 n에 대한 이하분포의 표준편차를 의미합니다. 실제 리그는 p=0.5가 될 것이고, 각 팀별로 144경기를 치르니 n=144가 될 것입니다. 그렇다면 실제 재능에 의한 승률은 실제 측정된 승률과 리그 평균과의 편차 중 재능에 의한 부분을 따로 뽑아서 리그 평균과의 재능 편차를 구함으로써 얻을 수 있을 겁니다. 그렇다면 다음의 식과 같이 생각할 수 있을 겁니다. $$win(talent) = mean + (win - mean) / S.D.(total) \cdot (t/v) \cdot S.D(talent)$$ $$win(talent) = 0.5 + (win-0.5)/v \cdot (t/v) \cdot t = 0.5 + (win - 0.5) \cdot (\frac{t}{v})^{2}$$ $$win(talent) = win \cdot \frac{t^{2}}{v^{2}} + 0.5 \cdot (1 - \frac{t^{2}}{v^{2}})$$ 다르게 보자면, $r = \frac{t^{2}}{v^{2}}$인 평균으로의 회귀를 이용한다고 볼 수도 있습니다. 여하튼 이런 방식으로 2000 시즌부터 2023시즌까지 팀의 승률을 뽑아냅니다. (이 설명은 이 포스트에서 나오는 방식과 같습니다.)

3. 왜 2000시즌부터 팀의 승률을 얻어냈냐면, 1999 시즌의 경우 쌍방울 구단이 너무 어려운 시즌을 기록하여 90년대 최악의 시즌 승률 (28승 7 무 97패, 승률 0.224)을 기록했는데 이게 너무 크기도 하고, 2000년대부터는 상대적으로 팀 간 승률 편차가 꽤 현재와 비슷하기 때문입니다.

그림 1. KBO 시즌별 팀 승률 표준편차. 팀승률의 편차는 점점 작아지는 추세를 보여주고 있습니다. 특히 2000년 정도를 기준으로 그 이후와 이전의 편차는 그 크기가 꽤 다르다는 걸 알 수 있습니다.

4. 하지만 이렇게 팀별 승률의 샘플을 얻어도 212개의 샘플이고, 그렇게 많은 샘플이라고 하기는 힘들 겁니다. 실제 시뮬레이션은 컴퓨터로 생성한 샘플들을 인풋으로 집어넣을 것이기에 팀별 승률 분포를 측정하기 위해 저는 커널 밀도 추정(KDE, Kernel Density Estimation)을 이용하기로 했습니다. KDE에서 Kernel은 평균값을 중심으로 대칭적인 모양을 가지는 분포를 가진 함수로, 각각의 샘플을 통계적으로 처리하기 위해 필요한 함수라고 생각하는 게 좋을 것 같습니다. 가장 쉽게 생각할 수 있는 예는 가우시안 분포가 있을 겁니다. 이를 왜 사용하냐면, 각각의 샘플을 통해 분포를 측정하게 될 텐데, 샘플의 때에 따라 실제 분포에서 튈 수밖에 없기 때문입니다. 아무리 극단값이 나올 확률이 적어도 그 극단값이 실제 샘플에서는 있을 수가 있는데, 이 극단값 때문에 분포 예측이 어그러질 수 있을 겁니다. 그렇기에 이 효과를 smoothing을 통해 조정할 필요가 있는데, 이런 smoothing에 필요한 함수들이라고 볼 수 있습니다. 이 kernel을 이용하기로 한다면, 각각의 샘플이 각각의 kernel을 가지고 있다고 생각할 수 있을 겁니다. 그리고 이 각각의 kernel의 합을 적절하게 정규화 시킴으로 분포를 추정할 수 있을 겁니다. 이런 식으로 kernel을 이용해 샘플의 분포를 추정하는 방법을 KDE라 합니다. 이 정규화를 할 때 어떤 bandwidth를 사용하느냐에 따라 결과가 크게 달라질 수 있는데, 제가 계산하는 분포는 꽤나 정규분포에 가까울 것이기 때문에 가장 쉽게 사용할 수 있는 bandwidth를 사용하여 정규화했습니다. (그 식은 wikipedia에서 확인할 수 있습니다.) KDE를 통한 승률 분포는 그림 2. 에서 확인하실 수 있습니다.

그림 2. 2000시즌부터 KBO팀의 재능에 의한 승률 분포(히스토그램)와 커널 밀도 추정(KDE)에 의해 추정한 KBO 재능의 분포(검은 선).

5. KBL의 경우 피타고리안 승률과 홈/원정 승률을 먼저 알아낼 필요가 있는데 이의 추정은 KBO에 대한 추정을 할 때와 같은 방식으로 계산을 했습니다.(그림 3. 과 4.) 그리고 이 기대승률을 토대로 위의 1~4의 과정을 똑같이 거쳐서 KBL의 승률 분포를 추정하였습니다.(그림 5.) 2001-02시즌 데이터부터 참고했는데, 이유는 2000-01시즌까지는 정규시즌에 45경기를 진행하고 중립경기까지 있었기 때문입니다.

그림 3.(왼쪽) 득실점에 따른 실제 승률 그래프. x축은 실점을 득점으로 나눈 값을, y축은 실제 승률을 의미합니다. 피팅한 값에 따르면 KBL의 피타고리안 승률 계수는 12.2 정도를 사용하는 게 좋을 것으로 보입니다. 그림 4.(오른쪽) 실제 팀 승률(x축)에 따른 홈승률(y) 그래프.
그림 5. KBL의 승률 분포 추정. 노란 히스토그램은 실제 KBL에서 측정한 재능에 의한 승률(2001-02시즌부터), 검은 선은 KDE를 통해 추정한 승률의 분포.

6. 그리고 이 값들을 이용해 매 시즌별 팀의 재능 격차를 얻어냅니다. 'KBO 포스트시즌 - KBL은 되는데 KBO는 왜 안 되나요?'에 나오는 그림 1. 과 그림 2. 가 그렇게 얻어낸 실제 시뮬레이션에 들어가는 데이터 샘플입니다. 승률을 실제로 얻어내는 것은 각 팀의 전체 팀에 대한 상대 위치(다른 말로 전체 팀에 대한 승률 순위의 위치) 값에서 실제 승률을 역으로 얻어내는 방식으로 얻어냈습니다.

6-1. 먼저 각 팀의 상대적 위치 자체는 균등 분포일 겁니다. 그리고 그 위치의 평균도 전체에 대한 50%에 해당할 겁니다. 다른 말로 100팀이 있을 때 평균 팀의 순위는 50위 정도일 거란 의미입니다. 이 팀들의 상대적 '위치값'을 10팀의 평균이 0.5가 되도록 얻어냅니다. 이는 10팀을 두 팀씩 나누거나(두 팀이라면 $x_{1}+x_{2}=1$이 되도록 얻을 수 있습니다.) 세 팀과 두 팀의 조합을 통해 나누는 것으로 결과를 얻어낼 수 있습니다. (세 팀의 평균 합이 1.5가 되도록 계산합니다.)
6-2. 6-1에서 얻어낸 각 팀의 상대적 위치는 분포의 CDF(Cumulative Density Function)에 대한 승률 값으로 환산하여 계산합니다. 마지막 10번째 샘플은 전체 승률 합이 5가 되도록 조정해 줍니다. 사실 바로 6-2를 얻을 수 있으면 좋겠지만(예를 들자면 정규 분포인 난수를 생성할 때 사용하는 방법인 box-muller method가 있습니다.) 역함수 꼴로 만들기 힘들어 부득이 이렇게 중간 과정을 넣었습니다. 사실 6-1,6-2 방식이 정석은 아니지만(정확히 말하면 6-1 과정에서 위치값의 평균이 0.5여야 할 '이유'가 없습니다.), 꽤나 많이 '닮은' 분포를 얻어내는 데 성공했습니다.

 

시뮬레이션

 

1. 시뮬레이션은 위의 방법을 통해 얻어낸 50000개의 샘플을 통해 합니다. 정확히는 평균 승률이 0.500에 위에서 얻어낸 승률 분포를 따르는 10개 팀의 승률을 50000회 얻어내고, 그 샘플들을 계속 인풋으로 넣어서 시뮬레이션하는 겁니다.

2. 평균적인 1~10위 팀에 의한 시뮬레이션 결과를 얻어낼 수도 있을 거고, 어쩌면 이게 더 정석적인 방법일 수 있습니다. 하지만 시즌의 결과는 각각의 샘플에 대해 한 번씩 얻어낼 수 있는 것이라 해석할 수 있고 무엇보다 매년마다 팀 간 승률 편차가 달라지기 때문에 편차에 따라서도 기대되는 결과가 계속 달라질 겁니다. 저는 이 팀의 승률 편차에 따른 결과도 알아보고 싶었고, 그 때문에 각각의 승률 샘플에 대해 딱 한 번씩만 순위를 내 보는 것으로 했습니다. (144경기는 물론 다 계산합니다.) 대신에 충분히 많은 횟수로 이를 계산하여 평균 낸다면 이 또한 통계적으로 의미 있는 값이 될 것이라고 생각했습니다.

3. 각각의 시뮬레이션은 50000회를 했습니다. 사실 10000번만 해도 그 결과의 신뢰도는 크게 차이가 없는데, 저는 팀의 승률 표준편차별로 그 결과를 종합해 보고 싶었기 때문에 (예를 들자면 승률 표준편차가 0.09~0.1 사이일 때의 우승 확률과 0.07~0.08 사이일 때의 우승 확률 비교 등) 50000회를 통해 좀 더 많은 분석을 하고자 했습니다.

4. 이를 통해 얻어낸 순위별 평균적인 승률과 10개 팀의 평균적인 기대승률은 다음과 같습니다.

표 1. 실제 순위별 평균 기대 승률과 시뮬레이션 된 승률 비교(KBO)
순위 실제 기대승률 평균
(2015~)
시뮬레이션 승률
1 0.615 0.616
2 0.582 0.578
3 0.549 0.552
4 0.530 0.531
5 0.504 0.511
6 0.498 0.491
7 0.474 0.471
8 0.450 0.449
9 0.423 0.422
10 0.374 0.379

KBL의 경우는 다음과 같습니다.

표 2. 실제 순위별 평균 기대 승률과 시뮬레이션 된 승률 비교(KBL)
순위 실제 기대승률 평균
(2001-02~)
시뮬레이션 승률
1 0.712 0.720
2 0.656 0.644
3 0.599 0.596
4 0.559 0.556
5 0.515 0.519
6 0.479 0.482
7 0.438 0.444
8 0.409 0.404
9 0.360 0.355
10 0.274 0.281
반응형

관련글 더보기

댓글 영역