zoukankan      html  css  js  c++  java
  • POJ 3164 最小树形图

    这题才是最小树形图的基础题,题意就不赘述了,敲这道题的时候发现一个很坑的情况。

    因为平时输入的时候用惯了输入优化,所以对于这些输入我一般都直接上输入优化的,但是这道题让我T了20次之后我才发现输入优化居然是T的原因,我改成scanf后就A掉了。

    比如下面那段代码的注释处,改成输入优化就T了。

    不解,求解答。

    #include <set>
    #include <map>
    #include <stack>
    #include <cmath>
    #include <queue>
    #include <cstdio>
    #include <string>
    #include <vector>
    #include <iomanip>
    #include <cstring>
    #include <iostream>
    #include <algorithm>
    #define Max 2505
    #define FI first
    #define SE second
    #define ll long long
    #define PI acos(-1.0)
    #define inf 0x7fffffff
    #define LL(x) ( x << 1 )
    #define bug puts("here")
    #define PII pair<int,int>
    #define RR(x) ( x << 1 | 1 )
    #define mp(a,b) make_pair(a,b)
    #define mem(a,b) memset(a,b,sizeof(a))
    #define REP(i,s,t) for( int i = ( s ) ; i <= ( t ) ; ++ i )
    
    using namespace std;
    
    inline void RD(int &ret) {
        char c;
        int flag = 1 ;
        do {
            c = getchar();
            if(c == '-')flag = -1 ;
        } while(c < '0' || c > '9') ;
        ret = c - '0';
        while((c=getchar()) >= '0' && c <= '9')
            ret = ret * 10 + ( c - '0' );
        ret *= flag ;
    }
    inline void OT(int a) {
        if(a >= 10)OT(a / 10) ;
        putchar(a % 10 + '0') ;
    }
    
    inline void RD(double &ret) {
        char c ;
        int flag = 1 ;
        do {
            c = getchar() ;
            if(c == '-')flag = -1 ;
        } while(c < '0' || c > '9') ;
        ll n1 = c - '0' ;
        while((c = getchar()) >= '0' && c <= '9') {
            n1 = n1 * 10 + c - '0' ;
        }
        ll n2 = 1 ;
        while((c = getchar()) >= '0' && c <= '9') {
            n1 = n1 * 10 + c - '0' ;
            n2 *= 10 ;
        }
        ret = flag * (double)n1 / (double)(n2) ;
    }
    /*********************************************/
    
    #define N 1005
    struct PP{
        double x , y ;
    }p[N] ;
    struct kdq{
        int s , e ;
        double l ;
    }ed[N * N] ;
    int n , m ;
    double getdis(int i ,int j){
        return sqrt((p[i].x - p[j].x) * (p[i].x - p[j].x) + (p[i].y - p[j].y) * (p[i].y - p[j].y)) ;
    }
    int pre[N] , vis[N] , id[N] ;
    double in[N] ;
    double Directed_MST(int root ,int V ,int E){
        double ret = 0 ;
        while(1){
            for (int i = 1 ; i < V ; i ++ )in[i] = inf ;
            for (int i = 0 ; i < E ; i ++ ){
                int s = ed[i].s ;
                int e = ed[i].e ;
                if(in[e] > ed[i].l && s != e){
                    pre[e] = s ;
                    in[e] = ed[i].l ;
                }
            }
            for (int i = 1 ; i < V ; i ++ ){
                if(i == root)continue ;
                if(in[i] == inf)return -1 ;
            }
            int cntnode = 1 ;
            mem(vis , -1) ;
            mem(id ,-1) ;
            in[root] = 0 ;
            for (int i = 1 ; i < V ; i ++ ){
                ret += in[i] ;
                int v = i ;
                while(vis[v] != i && id[v] == -1 && v != root){
                    vis[v] = i ;
                    v = pre[v] ;
                }
                if(v != root && id[v] == -1){
                    for (int u = pre[v] ; u != v ; u = pre[u]){
                        id[u] = cntnode ;
                    }
                    id[v] = cntnode ++ ;
                }
            }
            if(cntnode == 1)break ;
            for (int i = 1 ; i < V ; i ++ ){
                if(id[i] == -1)id[i] = cntnode ++ ;
            }
            for (int i = 0 ; i < E ; i ++ ){
                int s = ed[i].s ;
                int e = ed[i].e ;
                ed[i].s = id[s] ;
                ed[i].e = id[e] ;
                if(id[s] != id[e])ed[i].l -= in[e] ;
            }
            V = cntnode ;
            root = id[root] ;
        }
        return ret ;
    }
    
    int main() {
        while(scanf("%d%d",&n,&m) != EOF){
            for (int i = 1 ; i <= n ;i ++ ){
                scanf("%lf%lf",&p[i].x ,&p[i].y) ;
            }
            for (int i = 0 ; i < m ; i ++ ){
    //            RD(ed[i].s) ; RD(ed[i].s) ;
                scanf("%d%d",&ed[i].s ,&ed[i].e) ;
                if(ed[i].s != ed[i].e)//消除自环
                ed[i].l = getdis(ed[i].s , ed[i].e) ;
                else
                ed[i].l = inf ;
            }
            double ans = Directed_MST(1 , n + 1 , m) ;
            if(ans == -1)printf("poor snoopy
    ") ;
            else
            printf("%.2f
    ",ans) ;
        }
        return 0 ;
    }
    


  • 相关阅读:
    HDU 1501 Zipper(DFS)
    HDU 2181 哈密顿绕行世界问题(DFS)
    HDU 1254 推箱子(BFS)
    HDU 1045 Fire Net (DFS)
    HDU 2212 DFS
    HDU 1241Oil Deposits (DFS)
    HDU 1312 Red and Black (DFS)
    HDU 1010 Tempter of the Bone(DFS+奇偶剪枝)
    HDU 1022 Train Problem I(栈)
    HDU 1008 u Calculate e
  • 原文地址:https://www.cnblogs.com/james1207/p/3268852.html
Copyright © 2011-2022 走看看