【思路】
多个起点同时四周扩展广搜,注意会爆int
【AC】
1 #include<iostream>
2 #include<cstdio>
3 #include<cstring>
4 #include<string>
5 #include<cmath>
6 #include<algorithm>
7 #include<queue>
8 #include<map>
9 #include<stack>
10 using namespace std;
11 typedef long long ll;
12 const int maxn=1e3+2;
13 int n,m,k,d;
14 int mp[maxn][maxn];
15 bool vis[maxn][maxn];
16 int dis[maxn][maxn];
17 struct node{
18 int x;
19 int y;
20 int step;
21 node(int _x,int _y,int _s):x(_x),y(_y),step(_s){}
22 };
23 int cnt;
24 int dir[4][2]={{1,0},{-1,0},{0,1},{0,-1}};
25 queue<node> Q;
26 void init(){
27 while(!Q.empty()) Q.pop();
28 memset(mp,0,sizeof(mp));
29 memset(vis,false,sizeof(vis));
30 memset(dis,0,sizeof(dis));
31 cnt=0;
32 }
33 bool check(int x,int y){
34 if(x>=1&&x<=n&&y>=1&&y<=n) return true;
35 return false;
36 }
37 void bfs(){
38 while(!Q.empty()){
39 node q=Q.front();
40 Q.pop();
41 if(vis[q.x][q.y]) continue;
42 vis[q.x][q.y]=true;
43 if(mp[q.x][q.y]>0){
44 dis[q.x][q.y]=q.step;
45 cnt++;
46 if(cnt==k) return;
47 }
48 for(int i=0;i<4;i++){
49 int x=q.x+dir[i][0];
50 int y=q.y+dir[i][1];
51 if(check(x,y)&&mp[x][y]!=-1){
52 Q.push(node(x,y,q.step+1));
53 }
54 }
55 }
56 }
57 ll work(){
58 bfs();
59 ll ans=0;
60 for(int i=1;i<=n;i++){
61 for(int j=1;j<=n;j++){
62 if(mp[i][j]>0){
63 ans+=(ll)mp[i][j]*(ll)dis[i][j];
64 }
65 }
66 }
67 return ans;
68 }
69 int main(){
70 while(~scanf("%d%d%d%d",&n,&m,&k,&d)){
71 init();
72 int x,y,c;
73 for(int i=1;i<=m;i++){
74 scanf("%d%d",&x,&y);
75 Q.push(node(x,y,0));
76 }
77 for(int i=1;i<=k;i++){
78 scanf("%d%d%d",&x,&y,&c);
79 mp[x][y]+=c;
80 }
81 for(int i=1;i<=d;i++){
82 scanf("%d%d",&x,&y);
83 mp[x][y]=-1;
84 }
85 ll ans=work();
86 printf("%lld\n",ans);
87 }
88 return 0;
89 }
来源:oschina
链接:https://my.oschina.net/u/4288530/blog/4292004