共性
- 對于直接行走類的題,我們都可以用
int[][] dirs = new int[][]{{0,1}, {-1,0}, {0,-1}, {1,0}};
來表示向北 西 南 東
走一步 - 可以
int x = 0, y = 0, d = 0
xy 表示坐標,d表示方向,要和上面表示的方向對應 - 由于是對應的
d = 0 表示北
d = 1 表示西
d = 2 表示南
d = 3 表示東
即逆時針一圈 - 左轉:
d = (d+1) % 4
右轉:d = ((d - 1) % 4 + 4) % 4 => d = (d + 3) % 4
1041.困于環(huán)中的機器人
經過多次指令 instructions
后,判斷機器人是不是能回到原點。
解析:文章來源地址http://www.zghlxwxcb.cn/news/detail-594557.html
- 執(zhí)行一次指令后能否回到原點
(0, 0)
不看方向 - 執(zhí)行一次指令后,方向是不是不朝北
class Solution {
public boolean isRobotBounded(String instructions) {
int x = 0, y = 0, d = 0; // d用來控制方向,d為0表示向北
int[][] dirs = new int[][]{{0,1}, {-1,0}, {0,-1}, {1,0}};
for(char c : instructions.toCharArray()){
if(c == 'G'){
x += dirs[d][0];
y += dirs[d][1];
}else if(c == 'L'){
d = (d + 1) % 4; // 每次左轉,d就能加1
}else if(c == 'R'){
d = ((d - 1) % 4 + 4) % 4; // 每次右轉,d-1,但是為了讓d在 0 - 4里面,就需要+4
// d = (d + 3) % 4;
}
}
return (x==0&&y==0) || d != 0;
}
}
874.模擬行走的機器人
經過多次指令 commands
后,機器人離原點的最大歐式距離的平方,注意存在障礙物 obstacles
,有障礙物不能越過,只能停在前一個位置,但不影響后續(xù)指令
解析:
- 利用字符串拼接的模式存儲障礙物,以方便比較
- 一次一步的走,有障礙物就停住
class Solution {
public int robotSim(int[] commands, int[][] obstacles) {
// 存障礙物,直接將 x y 存為String形式
Set<String> set = new HashSet<>();
for(int[] o : obstacles) set.add(o[0] + "," + o[1]);
// 方向 南 北 西 東 ==> 要與d對應 0表示向北走一步 1西走 2南走 3東走
int[][] dirs = new int[][]{{0, 1}, {-1, 0}, {0, -1}, {1, 0}};
int ans = 0;
// x代表東西走,y代表南北走 d代表方向 0北 1西 2南 3東
int x = 0, y = 0, d = 0;
for(int i = 0; i < commands.length; i++){
if(commands[i] == -2){
// 左轉 順時針轉,方向都會 + 1
// d = d == 3 ? 0 : d + 1;
d = (d + 1) % 4; // 左轉相當于方向+1
}else if(commands[i] == -1){
// 右轉 逆時針轉,方向都會 - 1
// d = d == 0 ? 3 : d - 1;
d = (d + 3) % 4; // 右轉相當于左轉3次
}else{
// 沒有遇到障礙物會一直走,直到這一輪的步數走完
// 有障礙物就不會再走一步
while(commands[i] > 0 && !set.contains((x + dirs[d][0]) + "," + (y + dirs[d][1]))){
x += dirs[d][0];
y += dirs[d][1];
commands[i]--;
}
ans = Math.max(ans, x*x + y*y);
}
}
return ans;
}
}
模擬行走的機器人 2
在一個網格內行走,走到了邊界就逆時針旋轉90°,然后繼續(xù)向前走,設置行走的方法函數。文章來源:http://www.zghlxwxcb.cn/news/detail-594557.html
解析:
- 該題不用真的行走,只需要知道機器人的位置在哪里就行了
- 需要單獨判斷一下
(0, 0)
的朝向問題,因為可能剛好走回來到這個點,就超南,如果沒有移動過就超東
class Robot {
// 前進的四個方向
String[] ss = new String[]{"East", "North", "West", "South"};
int w, h, loc; // loc :有效(取模后)移動步數
boolean moved; // 記錄是否經過移動,用于判斷 (0, 0) 的方向
public Robot(int width, int height) {
w = width;
h = height;
}
public void step(int num) {
moved = true;
loc += num; // 只用知道總步數就行了,因為他一直在轉圈圈
loc = loc % (2 * (w - 1) + 2 * (h - 1)); // 路程超過了一圈,直接取模,看位置在哪里就行了,不用真的走
}
public int[] getPos() {
int[] info = move();
return new int[]{info[0], info[1]};
}
public String getDir() {
int[] info = move();
// x y 代表方向, dir 代表朝向
int x = info[0], y = info[1], dir = info[2];
// (0, 0) 時, 當未移動過方向為 East, 移動過方向為 South (從上指過來)
if(x == 0 && y == 0) return moved ? ss[3] : ss[0];
return ss[dir];
}
int[] move(){
if(loc <= w - 1){
// 當移動的步數在[0, w - 1] 時,所在位置在外圈下方,方向為East
return new int[]{loc, 0, 0};
}else if(loc <= (w - 1) + (h - 1)){
// 往右走到底,然后往上走,方向為:North
return new int[]{w-1, loc - (w - 1), 1};
}else if(loc <= 2 * (w - 1) + (h - 1)){
// 往右走到底,然后往上走到底,又往左走,方向:West
return new int[]{(w - 1) - (loc - ((w - 1) + (h - 1))), h - 1, 2};
}else {
// 最后一種情況是在左邊做外圈,往下走
return new int[]{0, (h - 1) - (loc - (2 * (w - 1) + (h - 1))), 3};
}
}
}
到了這里,關于1041.困于環(huán)中的機器人 && 874.模擬行走的機器人 && 模擬行走的機器人 2 (三道機器人的模擬題)的文章就介紹完了。如果您還想了解更多內容,請在右上角搜索TOY模板網以前的文章或繼續(xù)瀏覽下面的相關文章,希望大家以后多多支持TOY模板網!