22. 동점자 타이브레이커와 동시 점수 갱신 (C#)

난이도 상 해설 보기 →

결함을 모두 찾고 원인·수정안·더 나은 설계를 제시하라. 마커 (A)(B) 는 주목 위치 힌트다.

결함 코드 · C#
// ============================================================================
// [코드리뷰 문제] C# - 동점자 타이브레이커와 동시 점수 갱신
// ----------------------------------------------------------------------------
// 시나리오 (동시성/메모리 · 서버-서버):
//   - 실시간 랭킹에 각 플레이어의 "최고 점수(BestScore)" 와 "그 점수에 처음 도달한 시각
//     (ReachedAtMs)" 를 기록한다.
//   - 랭킹 규칙: 점수가 높을수록 상위. 동점이면 "그 점수에 더 먼저 도달한" 플레이어가 상위
//     (타이브레이커 = 더 이른 ReachedAtMs 우선).
//   - 점수 갱신은 여러 워커 스레드에서 동시에 들어온다. 새 점수가 기존 최고점보다 높을 때만
//     (BestScore, ReachedAtMs) 를 갱신한다. 같은 점수면 ReachedAtMs 를 더 늦게 만들면 안 된다.
//
// 요구사항:
//   - (BestScore, ReachedAtMs) 는 항상 짝이 맞아야 한다(찢어진 상태 금지).
//   - 동시 갱신에서 더 높은 점수가 유실되면 안 된다(lost update 금지).
//   - 타이브레이커가 정확해야 한다(동점 시 더 이른 도달 우선, 늦은 갱신이 시각을 덮지 않음).
//
// 과제:
//   이 코드의 잠재적 문제를 모두 찾고, 왜/어떻게 찢어진 상태·갱신 유실·타이브레이커 오류가
//   발생하는지(동시 인터리빙 포함) 설명하고, 수정안과 더 나은 설계를 제시하라.
//   (먼저 직접 리뷰를 적은 뒤 answer.md 와 대조할 것)
// ============================================================================

using System;
using System.Collections.Generic;

public class Entry
{
    // (A) 점수와 도달시각을 별개 필드로 보관 (둘의 조합은 원자가 아님)
    public int  BestScore;
    public long ReachedAtMs;
}

public class Leaderboard
{
    private readonly Dictionary<long, Entry> _table = new();   // 사전 등록됐다고 가정

    // 여러 워커 스레드에서 동시 호출
    public void Submit(long playerId, int newScore, long nowMs)
    {
        if (!_table.TryGetValue(playerId, out var e)) return;

        int cur = e.BestScore;

        // (B) 현재 최고점보다 높으면(또는 같으면) 갱신 — read 후 write 사이에 경쟁
        if (newScore >= cur)
        {
            e.BestScore = newScore;
            // (A)(C) 점수와 별개로 시각 갱신 — 동점이어도 시각을 덮어씀
            e.ReachedAtMs = nowMs;
        }
    }

    // 랭킹 비교: a 가 b 보다 상위면 true
    public static bool Higher(Entry a, Entry b)
    {
        // (A) 두 필드를 따로 읽어 찢어진 쌍을 볼 수 있음
        if (a.BestScore != b.BestScore) return a.BestScore > b.BestScore;
        return a.ReachedAtMs < b.ReachedAtMs;   // 동점: 더 이른 도달 우선
    }
}
내 리뷰 · C#
내 답안 · 자동 저장

작성 후 위 해설 보기에서 모범 해설과 대조하세요.