D. Bonfire
看到输出的字符串是对于每一个时间的判断,也就是肯定要枚举时间,在最外层的循环。
关键点是把每一团烟雾单独来看。假设当前在时刻 i,对于第 j( j <= i ) 时刻产生的烟雾,会受到 j,j + 1,…… i 时刻风的影响,也就是一个区间和,因此想到暴力写法:枚举 j
for (int i = 1; i <= n; i ++)
for (int j = 1; j <= i; j ++)
if (dx[i] - dx[j - 1] == r && dy[i] - dy[j - 1] == c)
{
s2.push_back('1');
continue;
}
else
s2.push_back('0');
因为已经在枚举 i,那么 dx [ i ] 和 dy [ i ] 就是固定值,只要做一个移向就可以得到 dx [ j - 1 ] = dx [ i ] - r,满足这个式子的 j 就是符合条件的,那只要用一个 map 看一下当前 pair 是否存在就可以了。
对于一个点要维护两个信息的情况(dx 和 dy),一定要先继承上一步,再判断,否则就会只转移一个。
#include<bits/stdc++.h>
#define int long long
using namespace std;
const int N = 2e5 + 5, INF = 1e18;
int T, n, r, c, cnt, ans, dx[N], dy[N];
string s, s2;
map<pair<int, int>, int> mp;
set<pair<int, int> > se;
signed main()
{
cin >> n >> r >> c >> s;
s = ' ' + s;
mp[{0, 0}] = 1;
for (int i = 1; i <= n; i ++)
{
dx[i] = dx[i - 1];
dy[i] = dy[i - 1];
if(s[i] == 'N') dx[i] --;
if(s[i] == 'S') dx[i] ++;
if(s[i] == 'W') dy[i] --;
if(s[i] == 'E') dy[i] ++;
mp[{dx[i], dy[i]}] = 1;
if (mp.count({dx[i] - r, dy[i] - c}))
s2.push_back('1');
else
s2.push_back('0');
}
cout << s2;
return 0;
}