우당탕탕 개발일지

[프로그래머스] Level 2. 광물 캐기 본문

Algorithm(c++)/Level 2

[프로그래머스] Level 2. 광물 캐기

devchop 2025. 1. 18. 11:36

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

 

프로그래머스

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

programmers.co.kr

 

 

해결방법

  • 광물을 캘 수 있는 최대 개수(max)를 구한다. 곡괭이 한 개 당 5개만 캘 수 있으므로, 모든 곡괭이를 다 쓰고도 광물을 캐지 못하면 나머지 광물은 캐지 못한다. 또는, 광물이 부족해서 곡괭이가 남을 수도 있다. 
  • 광물 리스트를 max개 까지 검사한다. 5개씩 묶어서 리스트 v에 넣는다. 311 이 저장되었을 경우 다이아 3개, 철 1개,  돌 1개라는 의미이다. 다이아가 많을 수록 피로도가 높기 때문에, 숫자가 높을수록 비싼광물이라는 것을 알 수 있다. 광물 개수가 총 10개라면, 리스트의 길이는 2 이다. 
  • v를 내림차순으로 정렬한다. 비싼 광물 순서대로 나열하기 위함이다.
  • 정렬된 v를 다시돌면서, 가장 좋은 곡괭이부터 사용하여 피로도를 계산하여 결과값 answer에 더해준다.

 

#include <string>
#include <vector>
#include  <algorithm>

using namespace std;

int solution(vector<int> picks, vector<string> minerals) {
    vector<vector<int>> prices ={{1,1,1},{5,1,1},{25,5,1}};
    vector<int> v;
    
    //캘수있는 광물 개수 구함 (max)
    int p_cnt = 0;
    for(int i=0; i<picks.size(); i++)p_cnt += picks[i]*5;
    int max = p_cnt < minerals.size() ? p_cnt: minerals.size();
    
    for(int i=0; i<max; i++){
        if(i% 5 == 0) v.push_back(0);
        
        if(minerals[i] == "diamond") v[i/5] += 100;
        else if(minerals[i] == "iron") v[i/5] += 10;
        else if(minerals[i] == "stone") v[i/5] += 1;
    }
    
    sort(v.rbegin(), v.rend());
    int answer =0 ;
    for(int i= 0; i<v.size(); i++){
        for(int j =0; j<picks.size(); j++){
            if(picks[j] == 0 ) continue;
            picks[j] --;
            int price = prices[j][0] * (v[i]/100) + prices[j][1] * (v[i]%100/10) + prices[j][2]*(v[i]%10);
            answer += price;
            break;
        }
    }
    
    
    return answer;
}