Skip to content

Commit f220948

Browse files
authored
feat: add solutions to lc problem: No.0874 (doocs#1206)
No.0874.Walking Robot Simulation
1 parent 6db604e commit f220948

File tree

7 files changed

+346
-206
lines changed

7 files changed

+346
-206
lines changed

solution/0800-0899/0874.Walking Robot Simulation/README.md

Lines changed: 110 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,23 @@
8484

8585
<!-- 这里可写通用的实现逻辑 -->
8686

87-
**方法一:模拟**
87+
**方法一:哈希表 + 模拟**
88+
89+
我们定义一个长度为 $5$ 的方向数组 $dirs=[0, 1, 0, -1, 0]$,数组中的相邻两个元素表示一个方向。即 $(dirs[0], dirs[1])$ 表示向北,而 $(dirs[1], dirs[2])$ 表示向东,以此类推。
90+
91+
我们使用一个哈希表 $s$ 来存储所有障碍物的坐标,这样我们就可以在 $O(1)$ 的时间内判断下一步是否会遇到障碍物。
92+
93+
我们使用两个变量 $x$ 和 $y$ 来表示机器人当前所在的坐标,初始时 $x = y = 0$。变量 $k$ 表示机器人当前的方向,答案变量 $ans$ 表示机器人距离原点的最大欧式距离的平方。
94+
95+
接下来,我们遍历数组 $commands$ 中的每个元素 $c$:
96+
97+
- 如果 $c = -2$,表示机器人向左转 $90$ 度,即 $k = (k + 3) \bmod 4$;
98+
- 如果 $c = -1$,表示机器人向右转 $90$ 度,即 $k = (k + 1) \bmod 4$;
99+
- 否则,表示机器人向前移动 $c$ 个单位长度。我们将机器人当前的方向 $k$ 与方向数组 $dirs$ 结合,即可得到机器人在 $x$ 轴和 $y$ 轴上的增量。我们将 $c$ 个单位长度的增量分别累加到 $x$ 和 $y$ 上,并判断每次移动后的新坐标 $(x, y)$ 是否在障碍物的坐标中,如果不在,则更新答案 $ans$,否则停止模拟,进行下一条指令的模拟。
100+
101+
最后返回答案 $ans$ 即可。
102+
103+
时间复杂度 $O(C \times n + m)$,空间复杂度 $O(m)$。其中 $C$ 表示每次可以移动的最大步数,而 $n$ 和 $m$ 分别表示数组 $commands$ 和数组 $obstacles$ 的长度。
88104

89105
<!-- tabs:start -->
90106

@@ -95,18 +111,18 @@
95111
```python
96112
class Solution:
97113
def robotSim(self, commands: List[int], obstacles: List[List[int]]) -> int:
98-
dirs = [[-1, 0], [0, 1], [1, 0], [0, -1]]
114+
dirs = (0, 1, 0, -1, 0)
99115
s = {(x, y) for x, y in obstacles}
100-
ans, p = 0, 1
116+
ans = k = 0
101117
x = y = 0
102-
for v in commands:
103-
if v == -2:
104-
p = (p + 3) % 4
105-
elif v == -1:
106-
p = (p + 1) % 4
118+
for c in commands:
119+
if c == -2:
120+
k = (k + 3) % 4
121+
elif c == -1:
122+
k = (k + 1) % 4
107123
else:
108-
for _ in range(v):
109-
nx, ny = x + dirs[p][0], y + dirs[p][1]
124+
for _ in range(c):
125+
nx, ny = x + dirs[k], y + dirs[k + 1]
110126
if (nx, ny) in s:
111127
break
112128
x, y = nx, ny
@@ -121,22 +137,22 @@ class Solution:
121137
```java
122138
class Solution {
123139
public int robotSim(int[] commands, int[][] obstacles) {
124-
int[][] dirs = {{-1, 0}, {0, 1}, {1, 0}, {0, -1}};
125-
Set<String> s = new HashSet<>();
126-
for (int[] v : obstacles) {
127-
s.add(v[0] + "." + v[1]);
140+
int[] dirs = {0, 1, 0, -1, 0};
141+
Set<Integer> s = new HashSet<>(obstacles.length);
142+
for (var e : obstacles) {
143+
s.add(f(e[0], e[1]));
128144
}
129-
int ans = 0, p = 1;
145+
int ans = 0, k = 0;
130146
int x = 0, y = 0;
131-
for (int v : commands) {
132-
if (v == -2) {
133-
p = (p + 3) % 4;
134-
} else if (v == -1) {
135-
p = (p + 1) % 4;
147+
for (int c : commands) {
148+
if (c == -2) {
149+
k = (k + 3) % 4;
150+
} else if (c == -1) {
151+
k = (k + 1) % 4;
136152
} else {
137-
while (v-- > 0) {
138-
int nx = x + dirs[p][0], ny = y + dirs[p][1];
139-
if (s.contains(nx + "." + ny)) {
153+
while (c-- > 0) {
154+
int nx = x + dirs[k], ny = y + dirs[k + 1];
155+
if (s.contains(f(nx, ny))) {
140156
break;
141157
}
142158
x = nx;
@@ -147,6 +163,10 @@ class Solution {
147163
}
148164
return ans;
149165
}
166+
167+
private int f(int x, int y) {
168+
return x * 60010 + y;
169+
}
150170
}
151171
```
152172

@@ -156,20 +176,27 @@ class Solution {
156176
class Solution {
157177
public:
158178
int robotSim(vector<int>& commands, vector<vector<int>>& obstacles) {
159-
vector<vector<int>> dirs = {{-1, 0}, {0, 1}, {1, 0}, {0, -1}};
160-
unordered_set<string> s;
161-
for (auto v : obstacles) s.insert(to_string(v[0]) + "." + to_string(v[1]));
162-
int ans = 0, p = 1;
179+
int dirs[5] = {0, 1, 0, -1, 0};
180+
auto f = [](int x, int y) {
181+
return x * 60010 + y;
182+
};
183+
unordered_set<int> s;
184+
for (auto& e : obstacles) {
185+
s.insert(f(e[0], e[1]));
186+
}
187+
int ans = 0, k = 0;
163188
int x = 0, y = 0;
164-
for (int v : commands) {
165-
if (v == -2)
166-
p = (p + 3) % 4;
167-
else if (v == -1)
168-
p = (p + 1) % 4;
169-
else {
170-
while (v--) {
171-
int nx = x + dirs[p][0], ny = y + dirs[p][1];
172-
if (s.count(to_string(nx) + "." + to_string(ny))) break;
189+
for (int c : commands) {
190+
if (c == -2) {
191+
k = (k + 3) % 4;
192+
} else if (c == -1) {
193+
k = (k + 1) % 4;
194+
} else {
195+
while (c--) {
196+
int nx = x + dirs[k], ny = y + dirs[k + 1];
197+
if (s.count(f(nx, ny))) {
198+
break;
199+
}
173200
x = nx;
174201
y = ny;
175202
ans = max(ans, x * x + y * y);
@@ -184,33 +211,28 @@ public:
184211
### **Go**
185212
186213
```go
187-
func robotSim(commands []int, obstacles [][]int) int {
188-
dirs := [][]int{{-1, 0}, {0, 1}, {1, 0}, {0, -1}}
189-
s := map[string]bool{}
190-
for _, v := range obstacles {
191-
t := strconv.Itoa(v[0]) + "." + strconv.Itoa(v[1])
192-
s[t] = true
214+
func robotSim(commands []int, obstacles [][]int) (ans int) {
215+
dirs := [5]int{0, 1, 0, -1, 0}
216+
type pair struct{ x, y int }
217+
s := map[pair]bool{}
218+
for _, e := range obstacles {
219+
s[pair{e[0], e[1]}] = true
193220
}
194-
ans, p := 0, 1
195-
x, y := 0, 0
196-
for _, v := range commands {
197-
if v == -2 {
198-
p = (p + 3) % 4
199-
} else if v == -1 {
200-
p = (p + 1) % 4
221+
var x, y, k int
222+
for _, c := range commands {
223+
if c == -2 {
224+
k = (k + 3) % 4
225+
} else if c == -1 {
226+
k = (k + 1) % 4
201227
} else {
202-
for i := 0; i < v; i++ {
203-
nx, ny := x+dirs[p][0], y+dirs[p][1]
204-
t := strconv.Itoa(nx) + "." + strconv.Itoa(ny)
205-
if s[t] {
206-
break
207-
}
208-
x, y = nx, ny
228+
for ; c > 0 && !s[pair{x + dirs[k], y + dirs[k+1]}]; c-- {
229+
x += dirs[k]
230+
y += dirs[k+1]
209231
ans = max(ans, x*x+y*y)
210232
}
211233
}
212234
}
213-
return ans
235+
return
214236
}
215237
216238
func max(a, b int) int {
@@ -221,6 +243,37 @@ func max(a, b int) int {
221243
}
222244
```
223245

246+
### **TypeScript**
247+
248+
```ts
249+
function robotSim(commands: number[], obstacles: number[][]): number {
250+
const dirs = [0, 1, 0, -1, 0];
251+
const s: Set<number> = new Set();
252+
const f = (x: number, y: number) => x * 60010 + y;
253+
for (const [x, y] of obstacles) {
254+
s.add(f(x, y));
255+
}
256+
let [ans, x, y, k] = [0, 0, 0, 0];
257+
for (let c of commands) {
258+
if (c === -2) {
259+
k = (k + 3) % 4;
260+
} else if (c === -1) {
261+
k = (k + 1) % 4;
262+
} else {
263+
while (c-- > 0) {
264+
const [nx, ny] = [x + dirs[k], y + dirs[k + 1]];
265+
if (s.has(f(nx, ny))) {
266+
break;
267+
}
268+
[x, y] = [nx, ny];
269+
ans = Math.max(ans, x * x + y * y);
270+
}
271+
}
272+
}
273+
return ans;
274+
}
275+
```
276+
224277
### **...**
225278

226279
```

0 commit comments

Comments
 (0)