BZOJ_4152

巧妙的性质:一个点最多只会与他横纵坐标最近的那4个点连边。所以我们sort sort连边建图。跑dijkstra

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <vector>
 4 #include <queue>
 5 #include <algorithm>
 6 #include <cmath>
 7 #include <iostream>
 8 using namespace std;
 9 const int maxn = 200003;
10 int n;
11 int first[maxn],to[maxn*8],next[maxn*8],dis[maxn*8],eg;
12 inline void addedge(int x,int y,int d) {
13     next[++eg] = first[x];first[x] = eg;
14     to[eg] = y;dis[eg] = d;
15 }
16 inline void add(int x,int y,int d) {
17     addedge(x,y,d);
18     addedge(y,x,d);
19 }
20 struct Point {
21     int x,y,key;
22     void read() {
23         scanf("%d%d",&x,&y);
24     }
25 }dian[maxn];
26 bool cmp1(const Point& p,const Point& q) {
27     return p.x < q.x;
28 }
29 bool cmp2(const Point& p,const Point& q) {
30     return p.y < q.y;
31 }
32 struct rp {
33     int v,key;
34     rp(int _v = 0,int _key = 0) {
35         v = _v;key = _key;
36     }
37 };
38 struct cmp {
39     bool operator()(const rp& a,const rp& b) {
40         return a.v > b.v;
41     }
42 };
43 priority_queue<rp,vector<rp>,cmp>dui;
44 int dist[maxn];
45 bool vis[maxn];
46 inline void dijkstra(int u) {
47     memset(dist,0x3f,sizeof(dist));
48     dist[u] = 0;
49     rp a = rp(0,1);
50     dui.push(a);
51     while(!vis[n]) {
52         rp zxr_handsome = dui.top();
53         dui.pop();
54         if(vis[zxr_handsome.key]) continue;
55         vis[zxr_handsome.key] = 1;
56         for(int i = first[zxr_handsome.key];i;i = next[i]) {
57             int v = to[i];
58             int newdist = dist[zxr_handsome.key] + dis[i];
59             if(newdist < dist[v]) {
60                 dist[v] = newdist;
61                 dui.push(rp(newdist,v));
62             }
63         }
64     }
65     cout << dist[n] << endl;
66 }
67 int main() {
68     scanf("%d",&n);
69     for(int i = 1 ; i <= n ; ++i) dian[i].read(),dian[i].key = i;
70     sort(dian+1,dian+1+n,cmp1);
71     /*for(int i = 1 ; i <= n ; ++i) {
72         printf("%d ",dian[i].x);
73     }
74     cout << endl << endl;*/
75     for(int i = 2 ; i <= n ; ++i)
76         add(dian[i].key,dian[i-1].key,dian[i].x - dian[i-1].x);
77     sort(dian+1,dian+1+n,cmp2);
78     for(int i = 2 ; i <= n ; ++i)
79         add(dian[i].key,dian[i-1].key,dian[i].y - dian[i-1].y);
80     dijkstra(1);
81 }
View Code

然后据说这道题SPFA过不了,,我就过了一发。。

 1 #include <cstdio>
 2 #include <cstring>
 3 #include <vector>
 4 #include <queue>
 5 #include <algorithm>
 6 #include <cmath>
 7 #include <iostream>
 8 using namespace std;
 9 const int maxn = 200003;
10 int n;
11 int first[maxn],to[maxn*8],next[maxn*8],dis[maxn*8],eg;
12 inline void addedge(int x,int y,int d) {
13     next[++eg] = first[x];first[x] = eg;
14     to[eg] = y;dis[eg] = d;
15 }
16 inline void add(int x,int y,int d) {
17     addedge(x,y,d);
18     addedge(y,x,d);
19 }
20 struct Point {
21     int x,y,key;
22     void read() {
23         scanf("%d%d",&x,&y);
24     }
25 }dian[maxn];
26 bool cmp1(const Point& p,const Point& q) {
27     return p.x < q.x;
28 }
29 bool cmp2(const Point& p,const Point& q) {
30     return p.y < q.y;
31 }
32 int dist[maxn];
33 bool ins[maxn];
34 inline void spfa(int u) {
35     deque<int>Q;
36     Q.push_front(u);
37     memset(dist,0x3f,sizeof(dist));
38     dist[u] = 0;
39     while(!Q.empty()) {
40         int u = Q.front();
41         Q.pop_front();
42         ins[u] = false;
43         for(int i = first[u];i;i = next[i]) {
44             int v = to[i];
45             int newdist = dist[u] + dis[i];
46             if(newdist < dist[v]) {
47                 dist[v] = newdist;
48                 if(!ins[v]) {
49                     if(Q.empty()) {
50                         Q.push_front(v);
51                     } else {
52                         int top = Q.front();
53                         if(dist[top] < dist[v]) Q.push_back(v);
54                         else Q.push_front(v);
55                     }
56                     ins[v] = 1;
57                 }
58             }
59         }
60     }
61     cout << dist[n];
62 }
63 int main() {
64     scanf("%d",&n);
65     for(int i = 1 ; i <= n ; ++i) dian[i].read(),dian[i].key = i;
66     sort(dian+1,dian+1+n,cmp1);
67     for(int i = 2 ; i <= n ; ++i)
68         add(dian[i].key,dian[i-1].key,dian[i].x - dian[i-1].x);
69     sort(dian+1,dian+1+n,cmp2);
70     for(int i = 2 ; i <= n ; ++i)
71         add(dian[i].key,dian[i-1].key,dian[i].y - dian[i-1].y);
72     spfa(1);
73 }
View Code

所以说双端队列就是好用。

转载于:https://www.cnblogs.com/registerzxr/p/5081880.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: bzoj作为一个计算机竞赛的在线评测系统,不仅可以提供大量的题目供程序员练习和学习,还可以帮助程序员提升算法和编程能力。为了更好地利用bzoj进行题目的学习和刷题,制定一个bzoj做题计划是非常有必要的。 首先,我们需要合理安排时间,每天留出一定的时间来做bzoj的题目。可以根据自己的时间安排,每天挑选适量的题目进行解答。可以先从难度较低的题目开始,逐渐提高难度,这样既能巩固基础知识,又能挑战自己的思维能力。 其次,要有一个计划和目标。可以规划一个每周或每月的题目数量目标,以及每个阶段要学习和掌握的算法知识点。可以根据bzoj的题目分类,如动态规划、图论、贪心算法等,结合自己的实际情况,有针对性地选择题目进行学习。 此外,要充分利用bzoj提供的资源。bzoj网站上有很多高质量的题解和优秀的解题代码,可以参考和学习。还有相关的讨论区,可以与其他程序员交流和讨论,共同进步。 最后,要坚持并保持思考。做题不是单纯为了刷数量,更重要的是学会思考和总结。遇到难题时,要有耐心,多思考,多尝试不同的解法。即使不能一次性解出来,也要学会思考和分析解题过程,以及可能出现的错误和优化。 总之,bzoj做题计划的关键在于合理安排时间、制定目标、利用资源、坚持思考。通过有计划的刷题,可以提高算法和编程能力,并培养解决问题的思维习惯,在计算机竞赛中取得更好的成绩。 ### 回答2: bzoj做题计划是指在bzoj这个在线测评系统上制定一套学习和刷题的计划,并且将计划记录在excel表格中。该计划主要包括以下几个方面的内容。 首先是学习目标的设定。通过分析自己的水平和知识缺口,可以设定一个合理的目标,比如每天解决一定数量的题目或者提高特定的算法掌握程度。 其次是题目选择的策略。在excel表格中可以记录下自己选择的题目编号、题目类型和难度等信息。可以根据题目的类型和难度来安排每天的刷题计划,确保自己可以逐步提高技巧和解题能力。 然后是学习进度的记录和管理。将每天的完成情况记录在excel表格中,可以清晰地看到自己的学习进度和任务完成情况。可以使用图表等功能来对学习进度进行可视化展示,更好地管理自己的学习计划。 同时,可以在excel表格的备注栏中记录下每道题目的解题思路、关键点和需要复习的知识点等信息。这样可以方便自己回顾和总结,巩固所学的知识。 最后,可以将excel表格与其他相关资料进行整合,比如算法教材、题目解析和学习笔记等。这样可以形成一个完整的学习档案,方便自己进行系统的学习和复习。 总之,bzoj做题计划excel的制定和记录可以帮助我们更加有条理和高效地进行学习和刷题。通过合理安排学习目标和题目选择策略,记录学习进度和思路,并整合其他学习资料,我们可以提高自己的解题能力,并在bzoj上取得更好的成绩。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值