bzoj3380+3381+3382+3383 Usaco2004 Open

四道比较水的题

T1:SPFA+状压

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<algorithm>
 4 #include<queue>
 5 #define INF 0x3f3f3f3f
 6 using namespace std;
 7 int n,m,K,id[20],dis[102][102],num,N,f[1<<14][15],ans,vis[102],mp[102][102];
 8 
 9 void get_dis(int num){
10     queue<int> Q; memset(vis,0,sizeof(vis));
11     Q.push(num); dis[num][num]=INF; vis[num]=1;
12     while (!Q.empty()){
13         int now=Q.front(); Q.pop();
14         for (int i=1; i<=n; i++){
15             if (mp[now][i]!=0){
16                 dis[num][i]=max(dis[num][i],min(dis[num][now],mp[now][i]));
17                 if (!vis[i]) Q.push(i),vis[i]=1;
18             }
19         }
20     }
21 }
22 
23 int main(){
24     scanf("%d%d%d", &n, &m, &K);
25     for (int i=1; i<=K; i++) scanf("%d", &id[i]);
26     memset(dis,0,sizeof(dis));
27     for (int i=1,u,v,w; i<=m; i++) scanf("%d%d%d", &u, &v, &w),mp[v][u]=mp[u][v]=w;
28     for (int i=1; i<=n; i++) get_dis(i);
29     N=(1<<K);
30     for (int i=1; i<=K; i++) f[1<<(i-1)][i]=1;
31     for (int s=1; s<N; s++){
32         num=0;
33         for (int i=1; i<=K; i++) if (s&(1<<(i-1))) num++;
34         for (int i=1; i<=K; i++) if (s&(1<<(i-1))){
35             for (int j=1; j<=K; j++) if (!(s&(1<<(j-1))))
36                 if (num<=dis[id[i]][id[j]]) f[s^(1<<(j-1))][j]|=f[s][i];
37         }
38         for (int i=1; i<=K; i++) if ((s&(1<<(i-1))) && f[s][i]){
39             int t=min(num,dis[id[i]][1]);
40             ans=max(ans,t);
41         }
42     }
43     printf("%d
", ans);
44     return 0;
45 }
View Code

T2:裸RMQ

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<algorithm>
 4 #include<cmath>
 5 using namespace std;
 6 const int maxn = 25010;
 7 int n,m,f[maxn][20];
 8 int main(){
 9     scanf("%d%d", &n, &m);
10     for (int i=1; i<=n; i++) scanf("%d", &f[i][0]);
11     for (int j=1; (1<<j)<=n; j++)
12         for (int i=1; i+(1<<(j-1))<=n; i++)
13             f[i][j]=min(f[i][j-1],f[i+(1<<(j-1))][j-1]);
14     for (int i=1,a,b; i<=m; i++){
15         scanf("%d%d", &a, &b);
16         int t=log(b-a+1)/log(2);
17         printf("%d
", min(f[a][t],f[b-(1<<t)+1][t]));
18     }
19     return 0;
20 }
View Code

T3:曼哈顿距离转切比雪夫距离

 1 #include<stdio.h>
 2 #include<algorithm>
 3 #include<string.h>
 4 #define INF 1000010
 5 using namespace std;
 6 int n,a,b,x,y,mxx,mxy,mnx,mny;
 7 int main(){
 8     scanf("%d", &n);
 9     mxx=mxy=-INF; mnx=mny=INF;
10     for (int i=1; i<=n; i++){
11         scanf("%d%d", &a, &b);
12         x=b+a; y=b-a;
13         mnx=min(mnx,x); mxx=max(mxx,x);
14         mny=min(mny,y); mxy=max(mxy,y);
15     }
16     printf("%d
", max(mxx-mnx,mxy-mny));
17     return 0;
18 }
View Code

T4:set+最短路

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<queue>
 4 #include<set>
 5 #include<algorithm>
 6 using namespace std;
 7 const int maxn = 50010;
 8 struct node{
 9     int x,y,id;
10     friend bool operator<(node a, node b){
11         if (a.x==b.x) return a.y<b.y;
12         return a.x<b.x;
13     }
14 };
15 int n,t,x[maxn],y[maxn],dis[maxn];
16 queue<int> Q;
17 set<node> st;
18 node mk(int x, int y, int id){
19     node a; a.x=x; a.y=y; a.id=id; return a;
20 }
21 int main(){
22     scanf("%d%d", &n, &t);
23     for (int i=1; i<=n; i++){
24         scanf("%d%d", &x[i], &y[i]);
25         st.insert(mk(x[i],y[i],i));
26     }
27     dis[0]=0; x[0]=y[0]=0;
28     Q.push(0);
29     while (!Q.empty()){
30         int now=Q.front(); Q.pop();
31         for (int i=-2; i<=2; i++) for (int j=-2; j<=2; j++){
32             int X=x[now]+i, Y=y[now]+j;
33             set<node>::iterator next=st.find(mk(X,Y,0));
34             if (next!=st.end()){
35                 dis[next->id]=dis[now]+1;
36                 Q.push(next->id);
37                 if (Y>=t){
38                     printf("%d
", dis[next->id]);
39                     return 0;
40                 }
41                 st.erase(next);
42             }
43         }
44     }
45     puts("-1");
46     return 0;
47 }
View Code
原文地址:https://www.cnblogs.com/mzl0707/p/6072348.html