zoukankan      html  css  js  c++  java
  • bzoj2750

    题解详见lsj大神blog

      1 #include<cstdio>
      2 #include<cstring>
      3 #include<cmath>
      4 #include<ctime>
      5 #include<cstdlib>
      6 #include<iostream>
      7 #include<algorithm>
      8 #include<vector>
      9 #include<queue>
     10 #define clr(a,x) memset(a,x,sizeof(a))
     11 #define rep(i,l,r) for(int i=l;i<r;i++)
     12 typedef long long ll;
     13 using namespace std;
     14 int read()
     15 {
     16     char c=getchar();
     17     int ans1=0,f=1;
     18     while(!isdigit(c)){
     19         if(c=='-') f=-1;
     20         c=getchar();
     21     }
     22     while(isdigit(c)){
     23         ans1=ans1*10+c-'0';
     24         c=getchar();
     25     }
     26     return ans1*f;
     27 }
     28 struct edge{
     29     int to,v,num;
     30 };
     31 struct node{
     32     int d,num;
     33     inline bool operator <(const node&A)const{
     34         return d>A.d;
     35     }
     36 };
     37 const int mod=1000000007,maxn=1550,maxm=5050,inf=1e9+9;
     38 int d[maxn],ans[maxm],a[maxn],b[maxn],cnt[maxn],n,m;
     39 vector<edge>e[maxn]; 
     40 priority_queue<node>Q;
     41 void dijkstra(int s)
     42 {
     43     while(!Q.empty()) Q.pop();
     44     rep(i,1,n+1) d[i]=inf;
     45     d[s]=0;
     46     node start;
     47     start.num=s;
     48     start.d=0;
     49     Q.push(start);
     50     while(!Q.empty()){
     51         node now=Q.top();
     52         Q.pop();
     53         if(d[now.num]==now.d){
     54             rep(i,0,e[now.num].size()){
     55                 if(now.d+e[now.num][i].v<d[e[now.num][i].to]){
     56                     d[e[now.num][i].to]=now.d+e[now.num][i].v;
     57                     node next;
     58                     next.num=e[now.num][i].to;
     59                     next.d=d[e[now.num][i].to];
     60                     Q.push(next);
     61                 }
     62             }
     63         }
     64     }
     65 }
     66 void dfs1(int k)
     67 {
     68     rep(i,0,e[k].size()){
     69         if(d[k]+e[k][i].v==d[e[k][i].to]){
     70             if(!cnt[e[k][i].to]++) dfs1(e[k][i].to);
     71         }
     72     }
     73 }
     74 void dfs(int k)
     75 {
     76     rep(i,0,e[k].size()){
     77         if(d[k]+e[k][i].v==d[e[k][i].to]){
     78             a[e[k][i].to]+=a[k];
     79             a[e[k][i].to]%=mod;
     80             if(!(--cnt[e[k][i].to]))dfs(e[k][i].to);
     81         }
     82     }
     83 }
     84 int dp(int k)
     85 {
     86     if(b[k]) return b[k];
     87     rep(i,0,e[k].size()){
     88         if(d[k]+e[k][i].v==d[e[k][i].to]){
     89             b[k]+=dp(e[k][i].to);
     90             b[k]%=mod;
     91         }
     92     }
     93     return ++b[k];
     94 }
     95 int main()
     96 {
     97     n=read(),m=read();
     98     clr(ans,0);
     99     rep(i,0,m){
    100         edge ed;
    101         int from=read();
    102         ed.to=read(),ed.v=read(),ed.num=i;
    103         e[from].push_back(ed);
    104     }
    105     rep(i,1,n+1){
    106         dijkstra(i);
    107         clr(cnt,0),clr(a,0),clr(b,0);
    108         dfs1(i);
    109         a[i]=1;
    110         dfs(i);
    111         dp(i);
    112         rep(i,1,n+1){
    113             rep(j,0,e[i].size()){
    114                 if(d[i]+e[i][j].v==d[e[i][j].to]){
    115                     ans[e[i][j].num]=ans[e[i][j].num]+(a[i]%mod)*(b[e[i][j].to]%mod);
    116                     ans[e[i][j].num]%=mod;
    117                 }
    118             }
    119         }
    120     }
    121     rep(i,0,m){
    122         printf("%d
    ",ans[i]);
    123     }
    124     return 0;
    125 }
    View Code

    2750: [HAOI2012]Road

    Time Limit: 10 Sec  Memory Limit: 128 MB
    Submit: 358  Solved: 164
    [Submit][Status][Discuss]

    Description

    C国有n座城市,城市之间通过m条单向道路连接。一条路径被称为最短路,当且仅当不存在从它的起点到终点的另外一条路径总长度比它小。两条最短路不同,当且仅当它们包含的道路序列不同。我们需要对每条道路的重要性进行评估,评估方式为计算有多少条不同的最短路经过该道路。现在,这个任务交给了你。

    Input

    第一行包含两个正整数n、m
    接下来m行每行包含三个正整数u、v、w,表示有一条从u到v长度为w的道路

    Output

    输出应有m行,第i行包含一个数,代表经过第i条道路的最短路的数目对1000000007取模后的结果

    Sample Input

    4 4
    1 2 5
    2 3 5
    3 4 5
    1 4 8

    Sample Output

    2
    3
    2
    1

    HINT

    数据规模

    30%的数据满足:n≤15、m≤30

    60%的数据满足:n≤300、m≤1000

    100%的数据满足:n≤1500、m≤5000、w≤10000

    Source

     
    [Submit][Status][Discuss]
  • 相关阅读:
    The Preliminary Contest for ICPC China Nanchang National Invitational and International Silk-Road Programming Contest
    HDU 5299 Circles Game
    UVALive
    算法笔记--匈牙利算法
    算法笔记--Splay && Link-Cut-Tree && fhq _treap
    P2685 [TJOI2012]桥
    2017-2018 ACM-ICPC German Collegiate Programming Contest (GCPC 2017)
    ACM-ICPC2018南京赛区 Mediocre String Problem
    Project Euler 345: Matrix Sum
    算法笔记--manacher算法
  • 原文地址:https://www.cnblogs.com/chensiang/p/4673184.html
Copyright © 2011-2022 走看看