1.迷宫
有一个n×m 的迷宫,其中 . 表示空地, * 表示障碍物。除此之外,有 qq 个单向传送门:如果进入格子 (a_i,b_i)那么会被立即传送到 (c_i,d_i)保证每个点至多是一个传送门的入口。如果传送门最终传送到障碍物上,那么将会卡在障碍物上不能移动在传送门内部传送的花费是 0,在空地上每次可以往周围四个格子移动,花费是 1。现在我们想知道从 (1,1)走到 (x,y) 的最短距离。如果无法到达终点,输出 “No solution”。只要经过终点就算到达,即如果终点上有传送门也没有关系。
只过了一半数据
#include<bits/stdc++.h>
using namespace std;
int n,m,qq;
char a[1007][1007];
bool vis[1007][1007];
struct node{
int x1,y1;
int x2,y2;
}b[1007],c[1007];
struct node1{
int x,y;
int s;
};
int ex,ey;
int dx[4]={0,0,1,-1};
int dy[4]={1,-1,0,0};
int bfs(){
queue<node1>q;
node1 now,next,next1;
now.x=0;now.y=0;now.s=0;
q.push(now);
memset(vis,0,sizeof(vis));
vis[0][0]=1;
while(!q.empty()){
now=q.front();q.pop();
for(int i=0;i<4;i++){
int nx=now.x+dx[i];
int ny=now.y+dy[i];
int j;
if(0<=nx&&nx<n&&0<=ny&&ny<m&&a[nx][ny]=='.'&&!vis[nx][ny]){
vis[nx][ny]=1;
next.x=nx,next.y=ny,next.s=now.s+1;
if(nx==ex&&ny==ey) return next.s;
int flag=0;
for(int j=0;j<qq;j++){
if(nx==b[j].x1&&ny==b[j].y1) {
flag=1;
if(!vis[b[j].x2][b[j].y2]){
vis[b[j].x2][b[j].y2]=1;
next1.x=b[j].x2,next1.y=b[j].y2,next1.s=now.s+1;
if(a[next1.x][next1.y]=='*') return -1;
else if(next1.x==ex&&next1.y==ey) return next.s;
else q.push(next1);
break;
}
}
}
if(!flag) q.push(next);
}
}
}
return -1;
}
int main(){
cin>>n>>m;
for(int i=0;i<n;i++){
for(int j=0;j<m;j++){
cin>>a[i][j];
}
}
cin>>qq;
for(int i=0;i<qq;i++){
cin>>b[i].x1>>b[i].y1>>b[i].x2>>b[i].y2;
b[i].x1-=1;b[i].x2-=1;b[i].y1-=1;b[i].y2-=1;
}
cin>>ex>>ey;
ex=ex-1;
ey=ey-1;
int ans=bfs();
if(ans==-1) cout<<"No solution"<<endl;
else cout<<ans<<endl;
}
2.爬楼梯
每次只能爬1,2,3,4个台阶,一共十个台阶,第五个和第七个台阶不能使用,到达第十个台阶的方法种类数。
#include<iostream>
using namespace std;
int f[20];
int main ()
{
f[0]=0;
f[1]=1;
f[2]=2;//1+1
f[3]=4;//1+2+1
f[4]=8;//1+2+4+1
f[5]=0;
for(int i=6;i<=10;i++)
{
if(i==7)continue;
else f[i]=f[i-1]+f[i-2]+f[i-3]+f[i-4];
}
cout<<f[10];
return 0;
}
3.方阵
广场上的小朋友们排成了整齐的方阵。具体来说,我们可以把每个小朋友看做是一个点,那么小朋友们就形成了 n×n 的点阵。方阵中,小朋友 AA 和小朋友 BB 互相可以看见,当且仅当二人之间的连线不经过别的小朋友,且他们之间的距离不超过 k(因为太远就看不见了)。我们想知道有多少对小朋友互相可以看见。(A,B)与 (B,A) 算同一对。
例如, n=2,k=1 时答案为 4, n=2,k=2时答案为 6(距离为 1的有 4对,距离为 sqrt 2 的有 2 对), n=3,k=2时答案为 20。
现在我们想要知道,当 n=1000,k=5000 时的答案是多少。由于答案过大,请回答对 10^9+7 取模后的结果。
#include<iostream>
using namespace std;
int gcd(int a,int b){return b==0 ?a:gcd(b,a%b);}
long long dist(int a,int b){return a*a+b*b;}
int main ()
{
long long num=0;
long long e=1e9+7;
long long int n,k;
cin>>n>>k;
k*=k;
for(int i=1;i<n;i++)
for(int j=1;j<n;j++)
{
if(gcd(i,j)==1&&dist(i,j)<=k)
num=(num+(n-j)*(n-i)%e)%e;
}
num*=2;
num+=(2*n*(n-1)%e);
cout<<num<<endl;
return 0;
}