주녘공부일지

[프로그래머스 C#] Lv.3 베스트앨범 본문

CodingTest/Programmers Lv.3

[프로그래머스 C#] Lv.3 베스트앨범

주녘 2024. 3. 13. 19:27

https://school.programmers.co.kr/learn/courses/30/lessons/42579

 

프로그래머스

코드 중심의 개발자 채용. 스택 기반의 포지션 매칭. 프로그래머스의 개발자 맞춤형 프로필을 등록하고, 나와 기술 궁합이 잘 맞는 기업들을 매칭 받으세요.

programmers.co.kr

1. 정답코드 및 핵심 아이디어, 유의사항

조건에 따라 베스트앨범을 순서대로 구하는 문제 

1. 가장 많이 재생된 장르

2. 장르 내에서 가장 많이 재생된 노래 2개 (같다면 고유번호가 낮은 노래)

 

- 가장 많이 재생된 장르를 파악하기 위한 playDict // <장르이름, 플레이횟수>

- 장르 내에서 가장 많이 재생된 노래를 파악하기 위한 genresDict // <장르이름, (고유번호, 재생횟수)>

 

주석 참조

    using System;
    using System.Linq;
    using System.Collections.Generic;

    public class Solution
    {
        public class DataClass
        {
            public int num; // 고유 번호
            public int playCount; // 재생 횟수

            public DataClass(int num, int playCount)
            {
                this.num = num;
                this.playCount = playCount;
            }
        }

        public int[] solution(string[] genres, int[] plays)
        {
            var answerList = new List<int>();
            var genresDict = new Dictionary<string, List<DataClass>>(); // 장르별 데이터묶음
            var playDict = new Dictionary<string, int>(); // 장르별 총 재생횟수

            // 각 사전에 데이터 세팅
            for (int i = 0; i < genres.Length; i++)
            {
                if (genresDict.ContainsKey(genres[i]) == false)
                {
                    genresDict.Add(genres[i], new List<DataClass>());
                    playDict.Add(genres[i], 0);
                }

                genresDict[genres[i]].Add(new DataClass(i, plays[i]));
                playDict[genres[i]] += plays[i];
            }
            
            // 장르의 개수만큼 반복
            for (int i = 0; i < genresDict.Count; i++)
            {
                // 1. 가장 많이 재생된 장르 추출 후 삭제
                string bestGenres = playDict.Aggregate((x, y) => x.Value > y.Value ? x : y).Key;
                playDict.Remove(bestGenres);

                // 2. 장르 내에서 가장 많이 재생된 노래 2개 수록
                var list = genresDict[bestGenres];

                if (list.Count != 1)
                    answerList.Add(list[0].num);
                else
                {
                    list.Sort((x, y) => CompareTo(x, y));
                    answerList.Add(list[0].num);
                    answerList.Add(list[1].num);
                }
            }

            return answerList.ToArray();
        }

        // 재생 횟수와 고유 번호에 따라 DataClass를 정렬하는 메서드
        public int CompareTo(DataClass d1, DataClass d2)
        {
            if (d1.playCount == d2.playCount)
                return d1.num > d2.num ? 1 : -1;

            return d1.playCount < d2.playCount ? 1 : -1;
        }
    }