zoukankan      html  css  js  c++  java
  • 【HDU4360】 最短路变形

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4360

    题目大意:屌丝DD从地点1到地点n去找他的女神QQ,总共n个点,两个点之间可能有多条路,每条路上记录一个距离w和一个状态c,DD只能按女神要求走,即 ‘L’->’O’->’V’->’E’->’L’->’O’->’V’->’E’->.... etc,走到终点时LOVE必须是完整的,而且最少有一个LOVE。

    解题思路:开始用优先队列+bfs做,TLE,这样做不能对点标记,只能对边标记,所以一个点的同一状态可能很多次入队列,无奈的TLE。这题其实仔细想想就是简单的spfa嘛,只不过多存了几个状态,因为只能沿着L->O->V->E走,每个点只有四个状态(‘L’,‘O’,'V',‘E’)而且一定是满足要求的。这题简单扼,但为嘛我还WA了两天?!!!!注意1这个自循环点,超级大bug,蛋疼不已。

      1 #include <iostream>
      2 #include <cstdio>
      3 #include <cstring>
      4 #include <algorithm>
      5 using namespace std;
      6 
      7 typedef long long lld;
      8 const int mn=3333;
      9 const int mm=33333;
     10 const lld oo=1e15;
     11 int  reach[mm], next[mm], flow[mm], ch[mm];
     12 lld  head[mn], que[mn], dis[mn][4], cnt[mn][4], inque[mn];
     13 int n, edge;
     14 
     15 void addedge(int u, int v, int c1, int c2,  char c)
     16 {
     17     ch[edge]=c, reach[edge]=v, flow[edge]=c1, next[edge]=head[u], head[u]=edge++;
     18     ch[edge]=c, reach[edge]=u, flow[edge]=c2, next[edge]=head[v], head[v]=edge++;
     19 }
     20 
     21 int find(char c)
     22 {
     23    if(c=='L') return 0;
     24    else if(c=='O') return 1;
     25    else if(c=='V') return 2;
     26    else return 3;
     27 }
     28 
     29 bool spfa()
     30 {
     31     int l=0, h=0;
     32     memset(inque,0,sizeof(inque));
     33     for(int i=1; i<=n; i++)
     34         for(int j=0; j<4; j++) dis[i][j]=oo, cnt[i][j]=0;
     35     inque[1]=1;
     36     dis[1][0]=0;
     37     que[l++]=1;
     38     while(l!=h)
     39     {
     40         int u=que[h++];
     41         if(h==mn) h=0;
     42         inque[u]=0;
     43         for(int i=head[u]; i>=0; i=next[i])
     44         {
     45             int s=find(ch[i]), v=reach[i], val=flow[i];
     46             if(dis[v][(s+1)%4]>=dis[u][s]+val)
     47             {
     48                 if(dis[v][(s+1)%4]==dis[u][s]+val)
     49                 {
     50                     if(cnt[u][s]+1>cnt[v][(s+1)%4]) cnt[v][(s+1)%4]=cnt[u][s]+1;
     51                     else continue;
     52                 }
     53                 else
     54                 {
     55                     dis[v][(s+1)%4]=dis[u][s]+val;
     56                     cnt[v][(s+1)%4]=cnt[u][s]+1;
     57                 }
     58                 if(!inque[v])
     59                 {
     60                     inque[v]=1;
     61                     que[l++]=v;
     62                     if(l==mn) l=0;
     63                 }
     64             }
     65         }
     66     }
     67     if(dis[n][0]==oo||!cnt[n][0]) return false;
     68     else return true;
     69 }
     70 
     71 int main()
     72 {
     73     int m, T, tcase=0;
     74     cin >> T;
     75     while(T--)
     76     {
     77         cin >> n >> m;
     78         edge=0;
     79         memset(head,-1,sizeof(head));
     80         int mp[4]={0,0,0,0}, ct=0;
     81         while(m--)
     82         {
     83             int u, v, val, se;
     84             char sh[3];
     85             scanf("%d%d%d%s",&u,&v,&val,sh);
     86             addedge(u,v,val,val,sh[0]);
     87             if(n==1&&u==1&&v==1)
     88             {
     89                 se=find(sh[0]);
     90                 if(!mp[se]) ct++, mp[se]=val;
     91                 else mp[se]=min(mp[se],val);
     92             }
     93         }
     94         if(ct==4)
     95         {
     96            lld sum=mp[0]+mp[1]+mp[2]+mp[3];
     97            printf("Case %d: Cute Sangsang, Binbin will come with a donkey after travelling %I64d meters and finding %d LOVE strings at last.\n",++tcase,sum,ct/4);
     98            continue;
     99         }
    100         bool ok=spfa();
    101         if(!ok) printf("Case %d: Binbin you disappoint Sangsang again, damn it!\n",++tcase);
    102         else printf("Case %d: Cute Sangsang, Binbin will come with a donkey after travelling %I64d meters and finding %d LOVE strings at last.\n",++tcase,dis[n][0],cnt[n][0]/4);
    103     }
    104     return 0;
    105 }
    106 /*
    107 100
    108 1 4
    109 1 1 1 L
    110 1 1 1 O
    111 1 1 1 V
    112 1 1 1 E
    113 */
    View Code
  • 相关阅读:
    C#图片处理之:亮度和对比度的校正
    C#图片处理之:旋转图片90度的整数倍 .
    C#图片处理之:色彩调整 .
    C# 图片处理之:彩色图片转为黑白图 .
    C#图片处理之: 锐化
    C#图片处理之:图片缩放和剪裁 .
    C# 图片处理之:旋转图片任意角度 .
    C#图片处理之:Gamma校正 .
    C#图片处理之: 另存为压缩质量可自己控制的JPEG .
    c#图片处理之:在图片上打上文字
  • 原文地址:https://www.cnblogs.com/kane0526/p/3101107.html
Copyright © 2011-2022 走看看