zoukankan      html  css  js  c++  java
  • BZOJ2115 [Wc2011] Xor

    开始补冬令营期间做的题目啦~

    好吧冬令营ydl大爷在讲台上面讲图的树分解,我们一帮二子在下面讨论这道题,讨论了2个小时2333

    进入正题。。。首先我们把图dfs一遍,记录下dfs产生的生成树

    我们会发现,所有边分成了两种:树边(生成树上的边)和回边(从某个节点到其祖先的边),并且不存在两棵子树之间有边。

    定义回边和其中的树边形成的环叫基本环,则基本环最多有m - n个

    然后题解上有一句话"不难发现,答案是由1到n号点的一条树链和几个基本环形成的",我去脑补半天啊!!!这是因为操作是xor,所以来回路径上的边都算了两次刚好抵消掉。

    于是题解君就卖了个萌"高斯消元即可"。。。什么鬼。。。然后网上都说是什么线性基,那个也不造是什么。。。

    其实就是贪心啦!

    因为是xor所以可以拆开来看每一位,每次加入一个数的时候,总是查看当前最高位是0的能否变成1,如果不行,查看当前次高位是0的能否变成1,以此类推。

    顺便记录下使得某一位是1的时候的一种方案,就可以直接O(64)的推出下一次能不能让某一位从0变成1了。

     1 /**************************************************************
     2     Problem: 2115
     3     User: rausen
     4     Language: C++
     5     Result: Accepted
     6     Time:328 ms
     7     Memory:11412 kb
     8 ****************************************************************/
     9  
    10 #include <cstdio>
    11 #include <algorithm>
    12  
    13 using namespace std;
    14 typedef long long ll;
    15 const int N = 50005;
    16 const int M = N << 2;
    17 const int Cnt = 100;
    18 const int Maxlen = M * 30;
    19  
    20 struct edge {
    21     int next, to;
    22     ll v;
    23     edge() {}
    24     edge(int _n, int _t, ll _v) : next(_n), to(_t), v(_v) {}
    25 } e[M];
    26  
    27 int n, m, cnt;
    28 int first[N];
    29 ll f[N], Ans;
    30 ll ans[Cnt], from[Cnt];
    31 bool vis[N];
    32  
    33 char buf[Maxlen], *c = buf;
    34 int Len;
    35  
    36 inline ll read() {
    37     ll x = 0;
    38     while (*c < '0' || '9' < *c) ++c;
    39     while ('0' <= *c && *c <= '9')
    40         x = x * 10 + *c - '0', ++c;
    41     return x;
    42 }
    43  
    44 #define y e[x].to
    45 void dfs(int p) {
    46     int x;
    47     vis[p] = 1;
    48     for (x = first[p]; x; x = e[x].next)
    49         if (!vis[y]) {
    50             f[y] = f[p] ^ e[x].v;
    51             dfs(y);
    52         }
    53 }
    54 #undef y
    55  
    56 void work(int x, int y, ll v) {
    57     int i;
    58     v = v ^ f[x] ^ f[y];
    59     for (i = 1; i <= cnt && v; ++i)
    60         if (v & ans[i]) v ^= from[i];
    61     if (!v) return;
    62     ++cnt, ans[cnt] = 1, from[cnt] = v;
    63     while ((ans[cnt] << 1) <= v) ans[cnt] <<= 1;
    64     for (i = cnt; i > 1; --i)
    65         if (ans[i] > ans[i - 1])
    66             swap(ans[i], ans[i - 1]), swap(from[i], from[i - 1]);
    67 }
    68  
    69 int main() {
    70     Len = fread(c, 1, Maxlen, stdin);
    71     buf[Len] = '';
    72     int i, x, y;
    73     ll z;
    74     n = read(), m = read();
    75     for (i = 1; i <= m; ++i) {
    76         x = read(), y = read(), z = read();
    77         e[i] = edge(first[x], y, z), first[x] = i;
    78         e[i + m] = edge(first[y], x, z), first[y] = i + m;
    79     }
    80     dfs(1);
    81     for (i = 1; i <= m; ++i)
    82         work(e[i].to, e[i + m].to, e[i].v);
    83     Ans = f[n];
    84     for (i = 1; i <= cnt; ++i)
    85         if (!(Ans & ans[i])) Ans ^= from[i];
    86     printf("%lld
    ", Ans);
    87     return 0;
    88 }
    View Code

     (p.s. 写了究极读入优化就变成了rank.1了啊哈哈哈哈哈)

    By Xs酱~ 转载请说明 博客地址:http://www.cnblogs.com/rausen
  • 相关阅读:
    输入npm install 报错node-sass@4.13.0 postinstall:`node scripts/build.js` Failed at the node-sass@4.13.0
    二、vue组件化开发(轻松入门vue)
    一、vue基础语法(轻松入门vue)
    (三)ES6基础语法。。。freecodecamp笔记
    (一)响应式web设计。。。freecodecamp笔记
    LeetCode42. 接雨水(java)
    (5)air202读取串口数据并上传到阿里云显示
    (四)HXDZ-30102-ACC检测心率血氧数据并通过串口助手显示
    (三)air202连接阿里云上传静态数据
    2016-2017 National Taiwan University World Final Team Selection Contest A
  • 原文地址:https://www.cnblogs.com/rausen/p/4292257.html
Copyright © 2011-2022 走看看