카테고리 없음

(C#) 카운트 다운

Realuda72 2025. 7. 11. 18:03

https://school.programmers.co.kr/learn/courses/30/lessons/131129?language=csharp

 

프로그래머스

SW개발자를 위한 평가, 교육의 Total Solution을 제공하는 개발자 성장을 위한 베이스캠프

programmers.co.kr

 

동적 프로그래밍으로 풀었다.

 

i = 0부터 target 까지, dp[i]에 i점을 얻기 위한 최소 다트 횟수, 최대 싱글 또는 불 횟수를 기록한다.

i가 20 이하라면 싱글 한번으로 된다.

i가 40 이하이고 2의 배수라면 더블 한번으로 된다.

i가 60 이하이고 3의 배수라면 트리플 한번으로 된다.

i가 50이라면 불 한번으로 된다.

그 외의 경우에는, i에서 j*t값을 빼준 점수에 싱글, 더블, 트리플 중 하나를 더하면 된다.

혹은 i에서 50을 빼준 점수에서 불을 한번 더하면 된다.

 

코드

using System;

public class Solution {
    public int[] solution(int target)
    {
        int[] answer = new int[] { };
        tuple[] dp = new tuple[100001];

        for (var i = 0; i <= target; i++)
        {
            if (i <= 20)
            {
                dp[i] = new tuple(1, 1);
                continue;
            }
            if (i <= 40 && i % 2 == 0)
            {
                dp[i] = new tuple(1, 0);
                continue;
            }
            if (i <= 60 && i % 3 == 0)
            {
                dp[i] = new tuple(1, 0);
                continue;
            }
            if (i == 50)
            {
                dp[i] = new tuple(1, 1);
                continue;
            }
            tuple temp;
            dp[i] = new tuple(dp[i - 1].u + 1, dp[i - 1].v);
            for (var j = 1; j <= 20; j++)
            {
                for (var t = 1; t <= 3; t++)
                {
                    if (i - j * t < 0) break;
                    temp = dp[i - j * t];
                    if (t == 1)
                    {
                        // 싱글
                        temp = new tuple(temp.u + 1, temp.v + 1);
                    }
                    else
                    {
                        // 더블 or 트리플
                        temp = new tuple(temp.u + 1, temp.v);
                    }

                    if (temp.u < dp[i].u || (temp.u == dp[i].u && temp.v > dp[i].v))
                    {
                        dp[i] = temp;
                    }
                }
            }
            if (i - 50 < 0) continue;
            temp = dp[i - 50];
            temp = new tuple(temp.u + 1, temp.v + 1);
            if (temp.u < dp[i].u || (temp.u == dp[i].u && temp.v > dp[i].v))
            {
                dp[i] = temp;
            }
        }
        answer = new int[2] { dp[target].u, dp[target].v };
        return answer;
    }

    struct tuple
    {
        public int u;
        public int v;
        public tuple(int u, int v)
        {
            this.u = u;
            this.v = v;
        }
    }
}