hdu 6026 Deleting Edges(最短路)

来源:互联网 发布:淘宝上的酒是真的吗 编辑:程序博客网 时间:2024/05/17 08:36

题意:给你一个图,然后删去一些边(可以不删)使其变成一棵树,要求每条边到0点的距离最短。

女生赛题目第4题,当时觉得很简单,只要跑一遍dijkstra,然后统计对于每个顶点最短路相同时的路径个数,最后乘一下就好。
结果敲了一遍交上去wa了……百思不得其解,最后也没想出来是哪里的问题。
结束之后把打印的代码给学长看,结果上来就被一通骂= =“你连dijkstra的原理都没搞懂吧……”
恩……确实是我zz了

 for(int j=0;j<n;j++)        {            if(g[x][j]==0) continue;            int v=j;            int w=g[x][j];            if(dis[v]>dis[x]+w)            {            //    a[v]=0;                dis[v]=dis[x]+w;                que.push(make_pair(dis[v],v));            }else if(dis[v]==dis[x]+w)            {                a[v]++;            }

之前就是这样写的……没有a[v]的置0过程,只要相等的时候就会加一,这个时候就存在问题,在更新的过程中,很有可能遇到当前的dis并不是最优值,但是有路径相等的情况,就会多加入这种情况,所以可以通过在每次重新更新路径之后把对应的a[v]置0,就可以解决。
然而这次交上去一发又wa……
好吧……再次研究我的挫代码……
在dijkstra里,每一个用来更新的顶点只会被从队列里拿出来一次,但是放进去的时候可能会被放入多次,此时对应的dis值不同,但是在代码里是判断队列是否为空,否则一直出队,所以对于后面的顶点,可以通过加一个vis数组或者当前pair中所存的值和当前dis的比较来判断是否已经访问过这个顶点,访问过就直接continue就好。但是……我并没有加这个vis数组……这样正常情况下的最短路算法是不会错的,但是在这个题目中,后面的点会被重复计算,导致结果增加……
QAQ

#include <cstdio>#include <iostream>#include <vector>#include <queue>#include <algorithm>#include<cmath>#include <cstring>#include <map>#include <set>#include <iomanip>#include <bitset>#define pb push_back#define PI acos(-1)#define fi first#define se second#define INF 0x3f3f3f3f#define INF64 0x3f3f3f3f3f3f3f3f#define PII pair<int,int>using namespace std;const int mod = 1e9+7;const int MAX_P = 2e4+10;const int maxn =1e5+10;const int MAX_V = 5e5+10;const int maxv = 1440;typedef long long ll;int n;char p[60][60];int g[60][60];int a[60];int dis[60];int vis[60];void dijkstra(int s){    memset(dis,0x3f,sizeof(dis)); //   memset(vis,0,sizeof(vis));    dis[s]=0; //   vis[s]=1;    priority_queue<PII,vector<PII>,greater<PII> > que;  //first中存放距离,小的先出队    que.push(make_pair(0,s));    while(!que.empty())    {        PII now=que.top();        que.pop();        int x=now.se;        if(now.fi>dis[x]) continue;        for(int j=0;j<n;j++)        {            if(g[x][j]==0) continue;            int v=j;            int w=g[x][j];            if(dis[v]>dis[x]+w)            {                a[v]=0;                dis[v]=dis[x]+w;                que.push(make_pair(dis[v],v));            }else if(dis[v]==dis[x]+w)            {                a[v]++;            }        }    }}int main() {    while(scanf("%d",&n)!=EOF)    {        memset(a,0,sizeof(a));        for(int i=0;i<n;i++)            scanf("%s",p[i]);        for(int i=0;i<n;i++)            for(int j=0;j<n;j++)            g[i][j]=p[i][j]-'0';        dijkstra(0);        ll sum=1;        for(int i=0;i<n;i++)        {            if(a[i]!=0) sum=(sum*(a[i]+1))%mod;        }        cout<<sum<<endl;    }    return 0;}
0 0
原创粉丝点击