• 【POJ 3764】 The xor-longest path


    【题目链接】

                http://poj.org/problem?id=3764

    【算法】

               首先,我们用Si表示从节点i到根的路径边权异或和

               那么,根据异或的性质,我们知道节点u和节点v路径上的边权异或和就是Sx xor Sy

               问题就转化为了 : 在若干个数中,找到两个数异或的最大值,可以用Trie树加速,具体细节笔者不再赘述

    【代码】

               

    #include <algorithm>
    #include <bitset>
    #include <cctype>
    #include <cerrno>
    #include <clocale>
    #include <cmath>
    #include <complex>
    #include <cstdio>
    #include <cstdlib>
    #include <cstring>
    #include <ctime>
    #include <deque>
    #include <exception>
    #include <fstream>
    #include <functional>
    #include <limits>
    #include <list>
    #include <map>
    #include <iomanip>
    #include <ios>
    #include <iosfwd>
    #include <iostream>
    #include <istream>
    #include <ostream>
    #include <queue>
    #include <set>
    #include <sstream>
    #include <stdexcept>
    #include <streambuf>
    #include <string>
    #include <utility>
    #include <vector>
    #include <cwchar>
    #include <cwctype>
    #include <stack>
    #include <limits.h>
    using namespace std;
    #define MAXN 200010
     
    int i,n,tot,u,v;
    int head[MAXN];
    long long s[MAXN];
    long long w,ans;
    
    struct Edge
    {
        int to;
        long long w;
        int nxt;
    } e[MAXN<<1];
    
    inline void add(int u,int v,long long w)
    {
        tot++;
        e[tot] = (Edge){v,w,head[u]};
        head[u] = tot;
    }
    inline void dfs(int u,int fa)
    {
        int i,v;
        long long w;
        for (i = head[u]; i; i = e[i].nxt)
        {
            v = e[i].to;
            w = e[i].w;
            if (v == fa) continue;
            s[v] = s[u] ^ w;
            dfs(v,u);    
        }    
    }
    class Trie
    {
        private :
            int tot;
            int child[MAXN*31][2];
        public :
            inline void clear()
            {
                tot = 0;
                memset(child,0,sizeof(child));
            }
            inline void insert(long long x)
            {
                int i,t,now = 0;
                for (i = 0; i < 31; i++)
                {
                    if (x & (1 << (30- i))) t = 1;
                    else t = 0; 
                    if (!child[now][t]) child[now][t] = ++tot;
                    now = child[now][t];    
                } 
            }
            inline long long getans(long long x)
            {
                int i,now = 0,t;
                long long ans = 0,val;
                for (i = 0; i < 31; i++)
                {
                    if (x & (1 << (30 - i))) t = 1;
                    else t = 0;
                    val = 1 << (30 - i);
                    if (child[now][t^1]) 
                    {
                        now = child[now][t^1];
                        ans |= val;
                    } else now = child[now][t];
                }
                return ans;
            } 
    } T;
    
    int main()
    {
        
        while (scanf("%d",&n) != EOF)
        {
            T.clear();
            tot = 0; ans = 0;
            for (i = 0; i < n; i++) head[i] = 0;    
            for (i = 1; i < n; i++)
            {
                scanf("%d%d%lld",&u,&v,&w);
                add(u,v,w);
                add(v,u,w);
            }
            dfs(0,-1);
            for (i = 0; i < n; i++) T.insert(s[i]);
            for (i = 0; i < n; i++) ans = max(ans,T.getans(s[i])); 
            printf("%lld
    ",ans);
        }
        
        return 0;    
    } 
  • 相关阅读:
    jmeter上传和下载、webservice、数据库连接 -- 9
    jmeter cookies和token -- 8
    java 获得 微信 UserId
    让textarea根据文本的长度自动调整它的高度
    oracle 连接数据库并查询,返回List<Map<String, Object>> 数据
    POI 4.0 读取Excel
    excel (2)
    导出 doc
    sui Mobile 试玩
    oracle 与 前台 md5
  • 原文地址:https://www.cnblogs.com/evenbao/p/9250966.html
Copyright © 2020-2023  润新知