BOJ 21942 : 부품 대여장

·2023년 1월 4일
0

알고리즘 문제 풀이

목록 보기
30/165
post-thumbnail

문제

풀이 과정

요약

Map 을 사용하는 문제.

상세

  1. 대여날짜를 분으로 환산한다. 벌금은 1분마다 늘어나기 때문에 비교하기 편하도록 분으로 확인하도록 했다. 분 환산 공식은 다음과 같다.

    day2460+hour60+minday*24*60+hour*60+min

  2. 입력값을 Map에 집어넣으면서 확인한다. Map 의 키 값은 item+user 형태로 하였다. 만약 동일한 키가 Map에 있다는 것은 해당 정보는 반납 날짜 정보라는 것이다. 이전 대여했던 시간과 반납하는 시간의 차를 구해 대여기간과 비교한다.

  3. 이전 대여했던 시간과 반납하는 시간 사이의 기간을 알기 위해, 자바 내장 함수를 사용했다. SimpleDateFormat
    먼저 해당 날짜들을 milliseconds 화 하고, 차를 구한 다음 해당 차를 다시 분으로 환산하였다. 분으로 환산한 값이 1 에서 구한 대여날짜보다 길다면 벌금을 내야한다. 벌금 비용을 나타내는 공식은 다음과 같다.

    (((currDateprevDate)/(100060))range)fee(((currDate - prevDate) / (1000*60)) - range) * fee

  4. 벌금을 내는 명단을 넣기 위한 Map 을 하나더 구현하여, keyset() 을 사용하여 이름순으로 정렬하였다.

정답

import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.text.SimpleDateFormat;
import java.util.*;

public class Main {
    public static void main(String[] args) throws Exception {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        StringTokenizer st = new StringTokenizer(br.readLine());
        int N = Integer.parseInt(st.nextToken());
        String L = st.nextToken();
        int ld = Integer.parseInt(L.substring(0,3));
        int lh = Integer.parseInt(L.substring(4,6));
        int lm = Integer.parseInt(L.substring(7, L.length()));
        int range = ld*24*60 + lh*60 + lm;
        int F = Integer.parseInt(st.nextToken());

        HashMap<String, String> map = new HashMap<>();
        HashMap<String, Long> fin = new HashMap<>();

        for(int i=0; i<N; i++) {
            st = new StringTokenizer(br.readLine());
            String date = st.nextToken();
            String time = st.nextToken();
            String item = st.nextToken();
            String user = st.nextToken();
            String id = item + "_" + user;

            if(map.containsKey(id)) {
                String dateStr1 = map.get(id);
                String dateStr2 = date + " " + time;
                SimpleDateFormat f = new SimpleDateFormat("yyyy-MM-dd HH:mm");
                long d1 = f.parse(dateStr1).getTime();
                long d2 = f.parse(dateStr2).getTime();

                long diff = ((d2-d1) / (1000*60));
                if(diff > range) {
                      if(fin.containsKey(user)) {
                          fin.put(user, fin.get(user)+(diff-range)*F);
                      } else {
                          fin.put(user,(diff-range)*F);
                      }
                }
                map.remove(id);
            } else {
                map.put(id, date + " " + time);
            }
        }

        List<String> list = new ArrayList<>(fin.keySet());
        list.sort((s1,s2) -> s1.compareTo(s2));
        if(fin.size() <= 0){
            System.out.println(-1);
        } else {
            StringBuilder sb = new StringBuilder();
            for(String key : list) {
                sb.append(key + " " + fin.get(key)).append("\n");
            }
            System.out.print(sb.toString());
        }
    }
}
profile
새로운 것에 관심이 많고, 프로젝트 설계 및 최적화를 좋아합니다.

0개의 댓글