[Softeer] 회의실 배정

leehyunjon·2023년 2월 6일
0

Algorithm

목록 보기
161/162

회의실 배정 : https://softeer.ai/practice/info.do?idx=1&eid=626&sw_prbl_sbms_sn=143458


Problem


Solve

Map<String, ArrayList<int[]>> map을 통해 회의실 이름을 key로 하여 시작시간과 끝시간을 배열로 하여 value에 저장해줍니다.

이때, 반환값이 회의실을 오름차순 정렬로 하라고 하였기 때문에 TreeMap을 이용하여 정렬을 수행시켜줍니다.

저장된 각 회의실의 사용 시간들을 이용하여 9시부터 18시까지 사용되지 않는 시간을 찾아주어여합니다.
특정 회의실의 사용시간에 대해 boolean[] useTime = new boolean[19]를 이용하여 사용시간을 ture로 갱신하여줍니다.
이때, 회의실 이용시간이 끝나는 시간(end)에 새로운 회의실을 시작할 수 있습니다. 그렇기 때문에 저는 useTime을 갱신할때, 시작시간+1부터 종료시간까지만 ture로 갱신하였습니다.
그 이유는 특정시간에 시작한다고 하였을때, 그 이후에 어떤 회의가 시작하는 시간이 있다면, 시작하는 시간까지는 회의실을 사용할수 있기 때문입니다.

List<int[]> timeList = new ArrayList<>();
//9시부터 18시까지 돌면서 사용가능한 시간 찾기
for (int t = 9; t <= 18; t++) {
	//특정 시작 시간
	int start = t;
    //특정 종료 시간 = 시작 시간+1
	int end = ++t;
    //종료시간이 18시 이후이거나 사용되지 않은 경우 종료시간을 늘려준다.
    //이때 사용중인 회의시간의 시작시간을 false로 선언해놓음으로써 종료시간을 사용중인 회의시간의 시작시간에 포함시킬 수 있습니다.
	while (t <= 18 && !useTime[t]) {
		end = t++;
	}

	//반복문을 돌면서 시간이 +1이 되기 때문에 1을 감소시키고 다음 반복을 수행해줍니다.
	t--;
    //start==t인 경우는 t+1시간이 true로 이미 사용하고 있는 시간이기때문에 조건을 만족하지 못하여 해당 시간은 사용하지 못합니다.
	if(start==t) continue;
	timeList.add(new int[] {start, end});

}

각 회의실에서 사용할 수 있는 시작시간과 끝시간의 리스트를 구하였습니다.
그 다음 각 회의실의 사용가능 시간을 String.format("%02d",time)을 이용하여 한자리 시간일때 앞에 0을 붙여 반환할 수 있도록 해줍니다.

그리고 마지막의 회의실에는 각 회의실을 분리하는 "-----"이 없기 때문에 최종 반복문을 종료하게 되면 delete([stringbuilder의 길이]-6,[stringbuilder])을 수행해줍니다.
여기서 6은 "-----""\n"의 길이입니다.


Code

import java.util.*;
import java.io.*;

public class Main {
	static Map<String, ArrayList<int[]>> map;

	public static void main(String args[]) throws IOException {
		BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
		BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));

		StringTokenizer st = new StringTokenizer(br.readLine(), " ");
		int N = Integer.parseInt(st.nextToken());
		int M = Integer.parseInt(st.nextToken());

		map = new TreeMap<>();

		for (int i = 0; i < N; i++) {
			String room = br.readLine();
			map.put(room, new ArrayList<>());
		}

		for (int i = 0; i < M; i++) {
			st = new StringTokenizer(br.readLine(), " ");
			String room = st.nextToken();
			int start = Integer.parseInt(st.nextToken());
			int end = Integer.parseInt(st.nextToken());

			map.get(room).add(new int[] {start, end});
		}

		StringBuilder sb = new StringBuilder();
		for (String room : map.keySet()) {
			List<int[]> timeListOfRoom = getRestTime(room);

			sb.append("Room ").append(room).append(":").append("\n");
			if (timeListOfRoom.size() > 0) {
				sb.append(timeListOfRoom.size()).append(" available:").append("\n");
				for (int[] time : timeListOfRoom) {
					String convertTime = convertTimeToString(time);
					sb.append(convertTime).append("\n");
				}
			} else {
				sb.append("Not available").append("\n");
			}
			sb.append("-----").append("\n");
		}
		int stringSize = sb.length();
		sb.delete(stringSize - 6, stringSize);

		bw.write(sb.toString());
		bw.flush();
		bw.close();
	}

	static String convertTimeToString(int[] time) {
		int start = time[0];
		int end = time[1];

		String startTime = String.format("%02d", start);
		String endTime = String.format("%02d", end);

		return startTime + "-" + endTime;
	}

	static List<int[]> getRestTime(String room) {
		List<int[]> timeListOfRoom = map.get(room);
		boolean[] useTime = new boolean[19];

		for (int[] t : timeListOfRoom) {
			for (int i = t[0] + 1; i <= t[1]; i++) {
				useTime[i] = true;
			}
		}

		List<int[]> timeList = new ArrayList<>();
		for (int t = 9; t <= 18; t++) {
			//t시간과 t+1시간 둘다 사용했다면 해당 t시간에는 회의가 끝나지 않음
			//if(useTime[t] && useTime[t+1]) continue;

			int start = t;
			int end = ++t;
			while (t <= 18 && !useTime[t]) {
				end = t++;
			}
			//if(t<=18) end = t;

			t--;
			if(start==t) continue;
			timeList.add(new int[] {start, end});

		}

		return timeList;
	}
}

Result


Reference

profile
내 꿈은 좋은 개발자

0개의 댓글