洛谷_Cx的故事_解题报告_第四题70
1.并查集求最小生成树
Code:
1 #include <stdio.h> 2 #include <stdlib.h> 3 4 struct node 5 { 6 long x,y,c; 7 }road[100001]; 8 9 long fa[100001]; 10 11 int cmp(const void *a,const void *b) 12 { 13 if ((*(struct node *)a).c < (*(struct node *)b).c) 14 return -1; 15 else 16 return 1; 17 } 18 19 long getfather(long d) 20 { 21 if (fa[d]==d) 22 return d; 23 fa[d]=getfather(fa[d]); 24 return fa[d]; 25 } 26 27 int main() 28 { 29 long n,m,t,xx,yy,x,y,i,cnt; 30 long long cost=0; 31 scanf("%ld%ld",&n,&m); 32 cnt=n-1; 33 for (i=1;i<=n;i++) 34 fa[i]=i; 35 for (i=1;i<=m;i++) 36 { 37 scanf("%ld%ld",&x,&y); 38 xx=getfather(x); 39 yy=getfather(y); 40 if (xx!=yy) 41 { 42 fa[xx]=yy; 43 cnt--; 44 if (cnt==0) 45 { 46 printf("0\n"); 47 return 0; 48 } 49 } 50 51 } 52 scanf("%ld",&t); 53 for (i=0;i<t;i++) 54 scanf("%ld%ld%ld",&road[i].x,&road[i].y,&road[i].c); 55 qsort(road,t,sizeof(struct node),cmp); 56 for (i=0;i<t;i++) 57 { 58 xx=getfather(road[i].x); 59 yy=getfather(road[i].y); 60 if (xx!=yy) 61 { 62 fa[xx]=yy; 63 cost+=road[i].c; 64 cnt--; 65 if (cnt==0) 66 { 67 printf("%lld\n",cost); 68 return 0; 69 } 70 } 71 } 72 printf("-1\n"); 73 return 0; 74 }
2.点有权值,spfa
1 #include <stdio.h> 2 #include <stdlib.h> 3 #include <stdbool.h> 4 5 struct node 6 { 7 long c; 8 struct node *next; 9 }*city[50001]; 10 11 long q[50001],pre[50001],m; 12 13 long min(long a,long b) 14 { 15 if (a>b) 16 return b; 17 else 18 return a; 19 } 20 21 void print(long d) 22 { 23 if (d!=m) 24 print(pre[d]); 25 printf("%ld",d); 26 if (d!=1) 27 printf("->"); 28 else 29 printf("\n"); 30 } 31 32 int main() 33 { 34 long i,j,s,t,b,e,n,ren,g[50001],head,tail,sum[50001]; 35 bool vis[50001]; 36 struct node *p; 37 scanf("%ld%ld%ld",&n,&m,&ren); 38 for (i=1;i<=n;i++) 39 { 40 scanf("%ld",&g[i]); 41 scanf("%ld",&s); 42 for (j=1;j<=s;j++) 43 { 44 scanf("%ld",&t); 45 p=(struct node *) malloc (sizeof(struct node)); 46 p->c=t; 47 p->next=city[i]; 48 city[i]=p; 49 } 50 } 51 for (i=1;i<=n;i++) 52 { 53 vis[i]=true; 54 sum[i]=5000000; 55 } 56 sum[m]=g[m]; 57 head=0; 58 tail=1; 59 q[1]=m; 60 61 do 62 { 63 head=(head+1)%50000; 64 // head++; 65 b=q[head]; 66 p=city[b]; 67 while (p) 68 { 69 e=p->c; 70 if (sum[b]+g[e]<sum[e]) 71 { 72 sum[e]=sum[b]+g[e]; 73 pre[e]=b; 74 if (vis[e]) 75 { 76 tail=(tail+1)%50000; 77 // tail++; 78 q[tail]=e; 79 vis[e]=false; 80 } 81 } 82 p=p->next; 83 } 84 vis[b]=true; 85 } 86 while (head!=tail); 87 88 if (sum[1]<=ren*10) 89 { 90 print(1); 91 printf("%ld\n",ren-sum[1]/10); 92 } 93 else 94 printf("No way!"); 95 return 0; 96 }
3.
地图bfs
U10278 Cx的金字塔 _ 落谷1126机器人搬重物 解题报告
I.哪个是行,哪个是列,行列从哪边开始
II.一次操作
1.前移1,2,3!步
2.转90度
III.边界范围 1~n-1 1~m-1
IV.起始点不可用
V.起始点=终止点
Code:
1 #include <stdio.h> 2 #include <stdlib.h> 3 #include <stdbool.h> 4 5 struct node 6 { 7 long x,y,c,step; 8 }q[100000]; 9 10 bool vis[60][60][4]; 11 12 long head,tail,s,t; 13 14 void add(long x,long y,long c) 15 { 16 tail++; 17 q[tail].x=x; 18 q[tail].y=y; 19 q[tail].c=c; 20 q[tail].step=q[head].step+1; 21 vis[x][y][c]=false; 22 if (x==s && y==t) 23 { 24 printf("%ld\n",q[tail].step); 25 exit(0); 26 } 27 } 28 29 int main() 30 { 31 long n,m,i,j,k,x,y,c; 32 long map[60][60]; 33 char ccs,cs; 34 scanf("%ld%ld",&n,&m); 35 for (i=1;i<=n;i++) 36 for (j=1;j<=m;j++) 37 for (k=0;k<4;k++) 38 vis[i][j][k]=true; 39 40 for (i=1;i<=n;i++) 41 for (j=1;j<=m;j++) 42 scanf("%ld",&map[i][j]); 43 scanf("%ld%ld%ld%ld%c%c",&x,&y,&s,&t,&ccs,&cs); 44 45 if (x==0 || x==n || y==0 || y==m || map[x][y]==1 || map[x+1][y]==1 || map[x][y+1]==1 || map[x+1][y+1]==1) 46 { 47 printf("-1"); 48 return 0; 49 } 50 51 if (x==s && y==t) 52 { 53 printf("0\n"); 54 return 0; 55 } 56 57 head=0; 58 tail=1; 59 q[1].x=x; 60 q[1].y=y; 61 if (cs=='E') 62 c=3; 63 else if (cs=='S') 64 c=1; 65 else if (cs=='W') 66 c=2; 67 else 68 c=0; 69 q[1].c=c; 70 q[1].step=0; 71 vis[x][y][c]=false; 72 //上:0 下:1 左:2 右:3 73 head=0; 74 tail=1; 75 do 76 { 77 head++; 78 x=q[head].x; 79 y=q[head].y; 80 c=q[head].c; 81 //上 82 if (c==0) 83 { 84 if (x>1 && map[x-1][y]==0 && map[x-1][y+1]==0) 85 { 86 if (vis[x-1][y][c]) 87 add(x-1,y,c); 88 if (x>2 && map[x-2][y]==0 && map[x-2][y+1]==0) 89 { 90 if (vis[x-2][y][c]) 91 add(x-2,y,c); 92 if (x>3 && map[x-3][y]==0 && map[x-3][y+1]==0 && vis[x-3][y][c]) 93 add(x-3,y,c); 94 } 95 } 96 } 97 //下 98 else if (c==1) 99 { 100 if (x<n-1 && map[x+2][y]==0 && map[x+2][y+1]==0) 101 { 102 if (vis[x+1][y][c]) 103 add(x+1,y,c); 104 if (x<n-2 && map[x+3][y]==0 && map[x+3][y+1]==0) 105 { 106 if (vis[x+2][y][c]) 107 add(x+2,y,c); 108 if (x<n-3 && map[x+4][y]==0 && map[x+4][y+1]==0 && vis[x+3][y][c]) 109 add(x+3,y,c); 110 } 111 } 112 113 } 114 //左 115 else if (c==2) 116 { 117 if (y>1 && map[x][y-1]==0 && map[x+1][y-1]==0) 118 { 119 if (vis[x][y-1][c]) 120 add(x,y-1,c); 121 if (y>2 && map[x][y-2]==0 && map[x+1][y-2]==0) 122 { 123 if (vis[x][y-2][c]) 124 add(x,y-2,c); 125 if (y>3 && map[x][y-3]==0 && map[x+1][y-3]==0 && vis[x][y-3][c]) 126 add(x,y-3,c); 127 } 128 } 129 } 130 //右 131 else 132 { 133 if (y<m-1 && map[x][y+2]==0 && map[x+1][y+2]==0) 134 { 135 if (vis[x][y+1][c]) 136 add(x,y+1,c); 137 if (y<m-2 && map[x][y+3]==0 && map[x+1][y+3]==0) 138 { 139 if (vis[x][y+2][c]) 140 add(x,y+2,c); 141 if (y<m-3 && map[x][y+4]==0 && map[x+1][y+4]==0 && vis[x][y+3][c]) 142 add(x,y+3,c); 143 } 144 } 145 } 146 if (c==0 || c==1) 147 { 148 if (vis[x][y][2]) 149 add(x,y,2); 150 if (vis[x][y][3]) 151 add(x,y,3); 152 } 153 else 154 { 155 if (vis[x][y][0]) 156 add(x,y,0); 157 if (vis[x][y][1]) 158 add(x,y,1); 159 } 160 } 161 while (head<tail); 162 printf("-1\n"); 163 164 return 0; 165 }
4.
对于70%的数据:
2<=a<=250
对于100%的数据:
2<=a<=2^60
对于70%的数据:
初始:
现有一个花坛(A坛)装满了白蛇根草,还有两个空花坛(B坛,C坛),
三个花坛共有250*250*250=15625000种
(x,y,z)->其它状态
当有其中两个花坛的数目为|A|/2时结束
by lzu_cgb
share & spread ideas