티스토리 뷰

swexpertacademy.com/main/code/problem/problemDetail.do?contestProbId=AWIeV9sKkcoDFAVH&categoryId=AWIeV9sKkcoDFAVH&categoryType=CODE&problemTitle=%ED%8A%B9%EC%9D%B4%ED%95%9C&orderBy=FIRST_REG_DATETIME&selectCodeLang=ALL&select-1=&pageSize=10&pageIndex=1

 

SW Expert Academy

SW 프로그래밍 역량 강화에 도움이 되는 다양한 학습 컨텐츠를 확인하세요!

swexpertacademy.com

 

 

✔ 문제 조건

  1. 자석은 4개가 있고, 각 자석은 8개의 날을 가지고 있다.
    2차원 배열: arr[5][8] : 자석 번호는 1부터 시작
  2. K번 명령을 내린다.
    • idx번째 자석을 dir 방향으로 돌린다. (dir-> 1: 시계 방향, -1: 반시계 방향)
    • command[K][2]
    • 하나의 자석이 1칸 회전할 때, 붙어있는 자석은, 서로 붙어잇는 날의 자성과 다를 경우 반대 방향 (dir * -1)으로 회전한다.
  3. 모든 회전이 끝난 후 점수를 계산한다.
    1. 1 번 자석에서 빨간색 화살표 위치에 있는 날의 자성이 N 극이면 0 점, S 극이면 1 점을 획득한다.
    2. 2 번 자석에서 빨간색 화살표 위치에 있는 날의 자성이 N 극이면 0 점, S 극이면 2 점을 획득한다.
    3. 3 번 자석에서 빨간색 화살표 위치에 있는 날의 자성이 N 극이면 0 점, S 극이면 4 점을 획득한다.
    4. 4 번 자석에서 빨간색 화살표 위치에 있는 날의 자성이 N 극이면 0 점, S 극이면 8 점을 획득한

 

✔ 접근 과정

  1. 한 번 회전을 할 시 rotate(idx, dir)
    1. idx번째 자석을 회전시킨 적이 있는지 검사하고, 검사한 적이 있다면 종료한다. 종료한 적이 없다면 회전 체크를 한다.
    2. 회전하기 전, 왼쪽 자석과 오른쪽 자석에 맞닿아 있는 자성이 같은지 다른지 미리 표기해놓는다.
    3. dir 방향으로 회전한다.
    4. 2번에서 왼쪽 자석과 같다고 표기해놓았으면 왼쪽 자석을 반대로 돌린다.
    5. 2번에서 오른쪽 자석과 같다고 표기해놓았으면 오른쪽 자석을 반대로 돌린다.
  2. 1번의 rotate(idx, dir) 함수를 K번 실행한다. 실행 시 마다 자석 회전 유무 배열을 초기화 해준다.
  3. 최종 점수를 계산한다.

 

✔ 주의할 점

  1. 명령어 한 번 실행 시에는, 각 자석을 최대 한번 씩만 회전시킬 수 있다. 이를 명령어 실행 전마다 자석 회전 유무 배열을 초기화해주며 관리한다.
    회전 유무를 관리하지 않는다면, 2번 자석을 돌릴 시,
    2번 회전 -> 1번 회전 -> 다시 2번 회전으로 중복되어 돌릴 수 있다.
  2. 시계 방향으로 돌리는 경우와 반시계 방향으로 돌리는 경우


3. 인접한 자석과 붙어있는 날의 자성 체크

 

import java.io.*;
import java.util.*;
// 210423

public class Solution_모의_4013_특이한자석 {
	static int K;
	static int[][] arr; // 톱니바퀴 번호, 8개의 N/S 정보
	static int[][] command;
	static boolean[] v;
	
	public static void main(String[] args) throws Exception {
		//System.setIn(new FileInputStream("res/input_모의_4013_특이한자석.txt"));
		BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
		StringTokenizer st = null;
		StringBuilder sb = new StringBuilder();
		
		int T = stoi(br.readLine());
		
		for(int tc=1; tc<=T; tc++) {
			
			K = stoi(br.readLine());
			arr = new int[5][8]; // 톱니바퀴는 1번부터
			command = new int[K][2];
			
			for(int i=1; i<=4; i++) {
				st = new StringTokenizer(br.readLine(), " ");
				for(int j=0; j<8; j++) {
					arr[i][j] = stoi(st.nextToken());
				}
			}
			
			// 회전 명령
			for(int i=0; i<K; i++) {
				st = new StringTokenizer(br.readLine(), " ");
				command[i][0] = stoi(st.nextToken());
				command[i][1] = stoi(st.nextToken());
			}
			
			solve();
			sb.append("#" + tc + " " + count() + "\n");
		}
		
		System.out.println(sb.toString());
		
		br.close();
	}
	
	static void solve() {
		for(int k=0; k<K; k++) {
			v = new boolean[5];
			rotate(command[k][0], command[k][1]);
		}
	}

	static int count() {
		int score = 0;
		
		if(arr[1][0]==1) score += 1;
		if(arr[2][0]==1) score += 2;
		if(arr[3][0]==1) score += 4;
		if(arr[4][0]==1) score += 8;
		
		return score;
	}
	
	static void rotate(int idx, int dir) {
		if(v[idx]) return;
		v[idx]=true;
		
		boolean left=false, right=false;
		
		if(idx-1>=1 && arr[idx-1][2] != arr[idx][6]) left = true;
		if(idx+1<=4 && arr[idx][2] != arr[idx+1][6]) right =true;
		
		int[] res = new int[8];
		if(dir==1) {
			// 시계방향 회전
			for(int i=0; i<8; i++) {
				int ni = (i+dir)%8;
				res[ni] = arr[idx][i];
			}
			for(int i=0; i<8; i++) {
				arr[idx][i] = res[i];
			}
			
		} else if (dir==-1) {
			// 반시계방향 회전
			res[7] = arr[idx][0];
			for(int i=1; i<8; i++) {
				int ni = (i+dir)%8;
				res[ni] = arr[idx][i];
			}
			
			for(int i=0; i<8; i++) {
				arr[idx][i] = res[i];
			}
		}
		
		if(left) rotate(idx-1, dir*-1);
		if(right) rotate(idx+1, dir*-1);		
	}
    
	static int stoi(String str) {
		return Integer.parseInt(str);
	}
}

 

댓글
공지사항
최근에 올라온 글
최근에 달린 댓글
Total
Today
Yesterday
«   2024/09   »
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
29 30
글 보관함