zoukankan      html  css  js  c++  java
  • 解题:SDOI 2010 魔法猪学院

    题面

    题外话:神**可持久化左偏树,你谷的人都太神了,学不来

    我把这个当做A*模板题的说,先讲一讲个人对A*的理解:如果说普通的BFS是Bellman_Ford,那A*就是一个Dijkstra。以寻找第$k$优解为例,本来我们是要搜$k$遍;现在我们给当前的实际代价加上一个估计的乐观代价,这个就叫做估价函数;以每个状态的估价函数为标准,用堆维护每个状态就能保证当前的到的一定是还能得到的最优解,这样一次搜索就可以得到答案。

    这里用每个点到达终点的距离作为估价函数即可

     1 #include<queue>
     2 #include<cstdio>
     3 #include<cstring>
     4 #include<algorithm>
     5 using namespace std;
     6 const int N=5005,M=200005;
     7 struct a
     8 {
     9     int node;
    10     double dist;
    11 };
    12 bool operator < (a x,a y)
    13 {
    14     return x.dist>y.dist;
    15 } 
    16 priority_queue<a> hp;
    17 int p[N],noww[M],goal[M];
    18 int P[N],Noww[M],Goal[M];
    19 double val[M],Val[M],dis[N];
    20 int n,m,t1,t2,cnt,Cnt,ans;
    21 double e,t3;
    22 bool vis[N];
    23 void link1(int f,int t,double v)
    24 {
    25     noww[++cnt]=p[f],p[f]=cnt;
    26     goal[cnt]=t,val[cnt]=v;
    27 }
    28 void link2(int f,int t,double v)
    29 {
    30     Noww[++Cnt]=P[f],P[f]=Cnt;
    31     Goal[Cnt]=t,Val[Cnt]=v;
    32 }
    33 void Dijkstra(int s)
    34 {
    35     for(int i=1;i<=n;i++) dis[i]=2e9;
    36     dis[n]=0,hp.push((a){n,dis[n]});
    37     while(!hp.empty())
    38     {
    39         a tt=hp.top(); hp.pop(); int tn=tt.node; 
    40         if(vis[tn]) continue; vis[tn]=true;
    41         for(int i=P[tn];i;i=Noww[i])
    42             if(dis[Goal[i]]>dis[tn]+Val[i])
    43                 dis[Goal[i]]=dis[tn]+Val[i],hp.push((a){Goal[i],dis[Goal[i]]}); 
    44     } 
    45 }
    46 void Astar(int s)
    47 {
    48     hp.push((a){1,dis[1]});
    49     while(!hp.empty())
    50     {
    51         a tn=hp.top(); hp.pop();
    52         double d=tn.dist-dis[tn.node];
    53         if(tn.node==n)
    54         {
    55             if(e<d) return ;
    56             else e-=d,ans++;
    57         }
    58         for(int i=p[tn.node];i;i=noww[i])
    59             hp.push((a){goal[i],d+val[i]+dis[goal[i]]});
    60     }
    61 }
    62 void SPJ()
    63 {
    64     if(e==1e7)//有毒啊
    65         printf("2002000"),exit(0);
    66 }
    67 int main ()
    68 {
    69     scanf("%d%d%lf",&n,&m,&e),SPJ();
    70     for(int i=1;i<=m;i++)
    71     {
    72         scanf("%d%d%lf",&t1,&t2,&t3);
    73         link1(t1,t2,t3),link2(t2,t1,t3);
    74     }
    75     Dijkstra(n),Astar(1);
    76     printf("%d",ans);
    77     return 0;
    78 } 
    View Code
  • 相关阅读:
    HDU 2116 Has the sum exceeded
    HDU 1233 还是畅通工程
    HDU 1234 开门人和关门人
    HDU 1283 最简单的计算机
    HDU 2552 三足鼎立
    HDU 1202 The calculation of GPA
    HDU 1248 寒冰王座
    HDU 1863 畅通工程
    HDU 1879 继续畅通工程
    颜色对话框CColorDialog,字体对话框CFontDialog使用实例
  • 原文地址:https://www.cnblogs.com/ydnhaha/p/9779532.html
Copyright © 2011-2022 走看看