1. 程式人生 > >演算法題(二十):機器人的活動範圍問題

演算法題(二十):機器人的活動範圍問題

題目描述

地上有一個m行和n列的方格。一個機器人從座標0,0的格子開始移動,每一次只能向左,右,上,下四個方向移動一格,但是不能進入行座標和列座標的數位之和大於k的格子。 例如,當k為18時,機器人能夠進入方格(35,37),因為3+5+3+7 = 18。但是,它不能進入方格(35,38),因為3+5+3+8 = 19。請問該機器人能夠達到多少個格子?

分析

1. 要判斷四個方向是否可以繼續前進,需要一個記錄各個位置是否可以訪問的一維陣列;

2. 可以用深度優先演算法遍歷二維陣列,遍歷過程中將遍歷過的格子設定成已訪問狀態(true); 


程式碼

public class RobortRegion {

	public static void main(String[] args) {
		// TODO Auto-generated method stub
		int rows = 3;
		int cols = 3;
		int threshold = 3;
		System.out.println(movingCount(threshold, rows, cols));
	}
	
	public static int movingCount(int threshold, int rows, int cols){
		boolean[] flag = new boolean[rows*cols];
		int res = moving(threshold, rows, cols, 0, 0, flag);
		return res;
	}
	
	//深度優先遍歷矩陣
	public static int moving(int threshold, int rows, int cols, int i, int j, boolean[] flag){
		int res = 0;
		if(check(threshold, rows, cols, i, j, flag)){
			flag[i*rows+j] = true;
			res = 1+moving(threshold, rows, cols, i+1, j, flag)+
					moving(threshold, rows, cols, i-1, j, flag)+
					moving(threshold, rows, cols, i, j+1, flag)+
					moving(threshold, rows, cols, i, j-1, flag);
		}
		return res;
	}
	
	//檢查位置是否可訪問
	public static boolean check(int threshold, int rows, int cols, int i, int j, boolean[] flag){
		if(0<=i && i<rows && j>=0 && j<cols &&
				getSum(i)+getSum(j)<=threshold &&
				flag[i*rows+j]==false){
			return true;
		}
		return false;
	}
	
	//得到位置(i,j)上的和(分開計算i,j)
	public static int getSum(int num){
		int res = 0;
		while(num>0){
			res += num%10;
			num /= 10;
		}
		return res;
	}

}