题意:
给你一个地图,地图上 ‘.‘表示能走的点。’#' 表示不能走的点,
然后给你最多26个出发点,然后给你走的方法, 如果按照给的方法,完全可行(不超界,不遇见'#'),就是可行点,
最后把所有可行点按升序输出,没有输出no。
题解:
我算了一下复杂度,感觉大暴力可能过,于是一个一个位移,跑了快60个测试点,,,,TLE。
就在纠结怎么优化,后来一次走一行或一列,就不会超时了,这样的话,要记录每一行和每一列#数量 的前缀和,
如果能走,前缀和之差一定是0.
#include<bits/stdc++.h>
using namespace std;
const int maxn=1010;
const int maxk=1e5+100;
const int inf=0xfffffff;
int n,m,k,cnt=0;
char ma[maxn][maxn];
int ps[maxn][maxn],pr[maxn][maxn];
int ans[30];
struct node{
char d;
int s;
}a[maxk];
int main(){
memset(ma,'#',sizeof(ma));
cin>>n>>m;
for(int i=1;i<=n;++i) {
scanf("%s",ma[i]+1),ma[i][m+1]='#';
for(int j=1;j<=m;++j){
ps[i][j]=ps[i][j-1];
pr[i][j]=pr[i-1][j];
if(ma[i][j]=='#') ps[i][j]++,pr[i][j]++;
}
}
cin>>k;
for(int i=1;i<=k;++i) {getchar();
scanf("%c %d",&a[i].d,&a[i].s);
}
for(int i=1;i<=n;++i){
for(int j=1;j<=m;++j){
if(ma[i][j]>='A'&&ma[i][j]<='Z'){
int tx=i,ty=j,f=1,x=i,y=j;
for(int ia=1;ia<=k;++ia){
if(a[ia].d=='N') tx-=a[ia].s;
else if(a[ia].d=='S') tx+=a[ia].s;
else if(a[ia].d=='W') ty-=a[ia].s;
else ty+=a[ia].s;
if(tx<1||tx>n||ty<1||ty>m||ma[tx][ty]=='#'){
f=0;break;
}
if(y==ty){
if(pr[x][y]-pr[tx-1][ty]!=0){
f=0;break;
}
}
if(x==tx){
if(ps[x][y]-ps[tx][ty-1]!=0){
f=0;break;
}
}
x=tx,y=ty;
}if(f) ans[cnt++]=ma[i][j];
}
}
}
if(!cnt){
printf("no solution\n");return 0;
}
sort(ans,ans+cnt);
for(int i=0;i<cnt;++i)printf("%c",ans[i]);
puts("");
return 0;
}