Codeforces Round #753 (Div. 3)(记忆化搜索+图论)
E. Robot on the Board 1
题意
有一个字符串,求从哪一点开始出发可以走尽可能多的方格,如果出了边界视为结束
分析
可以维护两个变量 \(dx\ dy\)
如果 \(dy>0\) 那么说明机器人向右走,所以将后面的 \(dy\) 列置为 \(1\),如果 \(dy<0\) 则将前面的 \(dy\) 列置为 \(1\)
\(dx\) 同理,最后找到没有被访问过的行列即可
如此糟粕的思路在机器人必出界的情况下还需要回滚
根据上述思路,同样维护 \(dx\ dy\),分别代表 \(x\ y\) 方向上需要的长度
如果 \(dx=n\) ,说明刚刚出界,这时在 \(x\) 方向上只有一行可以选择来保证答案是最大的
int n, m, k, _;
// int a[N];
string s;
int calc(int opt, int len)
{
int minn = 0, maxx = 0;
int now = 0;
for(int i = 0; s[i]; i ++){
if(opt){
if(s[i] == 'R'){
now ++;
}
else if(s[i] == 'L'){
now --;
}
}
else{
if(s[i] == 'U'){
now --;
}
else if(s[i] == 'D'){
now ++;
}
}
if(maxx - minn + 1 >= len) break;
minn = min(minn, now);
maxx = max(maxx, now);
}
return - minn + 1;
}
signed main()
{
// IOS;
rush(){
cin >> n >> m;
cin >> s;
int x = calc(0, n), y = calc(1, m);
cout << x << " " << y << endl;
}
// PAUSE;
return 0;
}
F. Robot on the Board 2
题意
有一张地图,求从那个点出发可以走尽可能多的格子,如果出界或者走到原来经过的格子视为出界,输出起点与最远距离
分析
妥妥的记忆化搜索, \(a[x][y]\) 定义为 \((x,y)\) 开始出发可以走过的最远距离
题目中的样例提示存在环的情况,环内的每一个点的最远距离都为环的长度
const int N = 2e3 + 5;
int n, m, k, _;
int a[N][N];
char s[N][N];
bool vis[N][N];
pii stk[N * N];
int p;
int dfs(int x, int y)
{
stk[++ p] = {x, y};
if(x <= 0 || x > n) return 0;
if(y <= 0 || y > m) return 0;
if(vis[x][y]) return a[x][y];
vis[x][y] = 1;
if(s[x][y] == 'U'){
a[x][y] += dfs(x - 1, y) + 1;
}
else if(s[x][y] == 'D'){
a[x][y] += dfs(x + 1, y) + 1;
}
else if(s[x][y] == 'L'){
a[x][y] += dfs(x, y - 1) + 1;
}
else{
a[x][y] += dfs(x, y + 1) + 1;
}
return a[x][y];
}
void update()
{
pii top = stk[p];
for(int k = p - 1; k; k --){
if(stk[k] == top){
for(int i = k; i <= p; i ++){
int x = stk[i].fi, y = stk[i].se;
a[x][y] = p - k;
}
break;
}
}
}
signed main()
{
// IOS;
rush(){
sdd(n, m);
for(int i = 1; i <= n; i ++){
for(int j = 1; j <= m; j ++){
sc(s[i][j]);
}
}
for(int i = 1; i <= n; i ++){
for(int j = 1; j <= m; j ++){
if(a[i][j] == 0){
p = 0;
dfs(i, j);
update();
}
}
}
int x = 0, y = 0;
for(int i = 1; i <= n; i ++){
for(int j = 1; j <= m; j ++){
if(a[x][y] < a[i][j]){
x = i;
y = j;
}
}
}
printf("%d %d %d\n", x, y, a[x][y]);
rep(i, 1, n) rep(j, 1, m) a[i][j] = vis[i][j] = 0;
}
// PAUSE;
return 0;
}

浙公网安备 33010602011771号