白準18428の監視を避ける


https://www.acmicpc.net/problem/18428

バックトレースシルバー1
近づきにくいけどどうして銀色なのか悩む1
そして多くの間違いを犯して、多くの人の解答を探しました.
私が考えているのは
壁を配置するときはチェックします.この壁は有効な配置ですか?
壁のレイアウトも上下左右チェックし、上下左右に先生や学生がいなければレイアウトする必要はありません.
ホリゾンと垂直検査をした後...
配置の有無によって、次の移した幽霊を2つ焼いて、次の格子に移動すればいいのです.
生徒数は固定的だと思って、固定配列のミスと配置時に上下左右に拡散する方式が近い.
そんなに近い時は別に確認していません
このような要因が集まるとスタックがオーバーフローします...問題が多い.
そして解答を见て、简単だと思いました.
考慮すべき部分が少ないので、シルバー1のはずです.

しゅろんり

  • N*N格の中に馬が3頭(Nc 3)いて、普通はすべてできます
  • 導入後の
  • の確認
  • 終了
  • 別にアクセスチェックはしていませんが、どうせ1、5、7または7、5、1は同じなので、アクセスチェックをすればもっと性能が上がるはずです.でも.やらなくても...通過...
    import java.util.*;
    import java.io.*;
    
    public class 감시피하기 {
    
    	static int N;
    	static int[][] array; 
    	static boolean[][] visited;
    	static int[] sx; 
    	static int[] sy;
    	static boolean flag;
    	public static void main(String[] args) throws Exception{
    		// TODO Auto-generated method stub
    
    		BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
    		N = Integer.parseInt(br.readLine());
    		StringTokenizer st;
    		int sindex= 0;
    		visited = new boolean[N][N];
    		array = new int[N][N];
    		for(int i=0;i<N;i++) {
    			st = new StringTokenizer(br.readLine());
    			for(int j=0;j<N;j++) {
    				String cur = st.nextToken();
    				int type = 3;
    				if(cur.equals("X")) type =3; //방어막 가능 공간
    				else if(cur.equals("S")) {
    					type = 0; //학생
    					sindex++; //학생인원수 카운팅
    					visited[i][j] = true;
    				}
    				else {
    					type = 1; //선생
    					visited[i][j] = true;
    				}
    				array[i][j] = type;
    			}
    		}
            // 학생의 위치를 배열로넣어주기
    		sx = new int[sindex];
    		sy = new int[sindex];
    		sindex=0;
    		for(int i=0;i<N;i++) {
    			for(int j=0;j<N;j++) {
    				if(array[i][j]==0) {
    					sx[sindex] = i;
    					sy[sindex] = j;
    					sindex++;
    				}
    			}
    		}
    
    		flag =false;
    		start(0);
    		if(flag) System.out.println("YES");
    		else System.out.println("NO");
    
    	}
    	
    	public static void start(int c) {
    		if(c==3) {
    
    			for(int i=0;i<sx.length;i++) {
    				int curx = sx[i];
    				int cury = sy[i];
    				
    				//상 검색
    				
    				for(int j=curx+1;j<N;j++) {
    					if(array[j][cury]==2) break;
    					if(array[j][cury]==1) {
    						return;
    					}
    				}
    				
    				//하 검색
    				
    				for(int j=curx-1;j>=0;j--) {
    					if(array[j][cury]==2) break;
    					if(array[j][cury]==1) {
    						return;
    					}
    				}
    				
    				//우 검색
    				
    				for(int j=cury+1;j<N;j++) {
    					if(array[curx][j]==2) break;
    					if(array[curx][j]==1) {
    						return;
    					}
    				}
    				// 좌 검색
    				for(int j=cury-1;j>=0;j--) {
    					if(array[curx][j]==2) break;
    					if(array[curx][j]==1) {
    						return;
    					}
    				}
    			}
    			flag= true;
    			return ;
    		}
    		
    		for(int i=0;i<N;i++) {
    			for(int j=0;j<N;j++) {
    				if(array[i][j]==3) {
    					array[i][j]=2;
    					start(c+1);
    					array[i][j]=3;
    				}
    			}
    		}
    
    		
    	}
    
    }

    どうやって裏口を外したらいいか分からなくて、だんだん感覚が出てきたので、キブニは良くなってきました...ほほほ