Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) G - Xor-matic Number of the Graph 线性基好题

G - Xor-matic Number of the Graph

上一道题的加强版本,对于每个联通块需要按位算贡献。

#include<bits/stdc++.h>
#define LL long long
#define fi first
#define se second
#define mk make_pair
#define PII pair<int, int>
#define PLI pair<LL, int>
#define ull unsigned long long
using namespace std;

const int N = 1e5 + 7;
const int inf = 0x3f3f3f3f;
const LL INF = 0x3f3f3f3f3f3f3f3f;
const int mod = 1e9 + 7;

int n, m;
LL d[N], bin[N], num[2];
bool vis[N];
vector<PLI> edge[N];
vector<int> id;
struct Base {
    LL a[63];
    int cnt;
    void init() {
        memset(a, 0, sizeof(a));
        cnt = 0;
    }
    void add(LL x) {
        for(int j = 62; ~j; j--) {
            if((x >> j) & 1) {
                if(!a[j]) {a[j]=x; cnt++; break;}
                else x ^= a[j];
            }
        }
    }
} base;

void dfs(int u, int fa) {
    vis[u] = true;
    id.push_back(u);
    for(int i = 0; i < edge[u].size(); i++) {
        int v = edge[u][i].se; LL w = edge[u][i].fi;
        if(v == fa) continue;
        if(vis[v]) {
            base.add(d[u]^d[v]^w);
        } else {
            d[v] = d[u] ^ w;
            dfs(v, u);
        }
    }
}

int main() {
    base.pirnt();
    scanf("%d%d", &n, &m);
    for(int i=bin[0]=1; i <= n; i++)
        bin[i] = bin[i-1] * 2 % mod;
    for(int i = 1; i <= m; i++) {
        int u, v; LL w;
        scanf("%d%d%lld", &u, &v, &w);
        edge[u].push_back(mk(w, v));
        edge[v].push_back(mk(w, u));
    }

    LL ans = 0;
    for(int i = 1; i <= n; i++) {
        if(!vis[i]) {
            base.init();
            id.clear();
            dfs(i, 0);
            for(int j = 0; j <= 62; j++) {
                num[0] = 0, num[1] = 0;
                for(auto &x : id) {
                    num[(d[x]>>j)&1]++;
                }
                bool flag = false;
                for(int k = 0; k < 63; k++) {
                    if((base.a[k]>>j)&1) {
                        flag = true;
                        break;
                    }
                }

                LL tmp = num[0]*(num[0]-1)/2 + num[1]*(num[1]-1)/2;
                tmp %= mod;
                if(flag) ans = (ans + bin[j]*bin[base.cnt-1]%mod*tmp%mod) % mod;
                tmp = num[0] * num[1] % mod;
                if(flag) ans = (ans + bin[j]*bin[base.cnt-1]%mod*tmp%mod) % mod;
                else ans = (ans + bin[j]*bin[base.cnt]%mod*tmp%mod) % mod;
            }
        }
    }
    printf("%lld\n", ans);
    return 0;
}

/*
*/

原文地址:https://www.cnblogs.com/CJLHY/p/9741984.html

时间: 2024-10-09 12:59:33

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) G - Xor-matic Number of the Graph 线性基好题的相关文章

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) C. Ray Tracing

C. Ray Tracing There are k sensors located in the rectangular room of size n × m meters. The i-th sensor is located at point (xi, yi). All sensors are located at distinct points strictly inside the rectangle. Opposite corners of the room are located

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined)

C 模拟 题意:给的是一个矩形,然后√2 的速度走,如果走到边上就正常反射,走到角上,暂停反射,我们知道要不循环要不暂停,记录走到的点最短时间 /************************************************************************* > File Name: c.cpp > Author: opas_chenxin > Mail: [email protected] > Created Time: 2016年10月08日

codeforces Intel Code Challenge Final Round (div.1 + div.2 combined)

比赛水掉3题rk559 rating+115 赛后切掉C n年没打cf了终于又重新变蓝了,果然太弱... 1.A题  Checking the Calendar 给定两个星期几,问是否可能分别是两个月的第一天. 水题暴力枚举月份 #include<cstdio> #include<cstring> #include<cstdlib> #include<vector> #include<algorithm> #include<function

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) A

Description You are given names of two days of the week. Please, determine whether it is possible that during some non-leap year the first day of some month was equal to the first day of the week you are given, while the first day of the next month w

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined)D Dense Subsequence

传送门:D Dense Subsequence 题意:输入一个m,然后输入一个字符串,从字符串中取出一些字符组成一个串,要求满足:在任意长度为m的区间内都至少有一个字符被取到,找出所有可能性中字典序最小的情况,并按字典序输出 思路:字典序 例如 aaaaaaab < ab  也就是说,如果满足要求的取法中取到了b 那么所有的a都应该被取到,这样才可以保证字典序最小,那么也就是说在26个字母中找到一定要被取的最大字母,然后再确定最大的字母的个数,比它小的全部要取 AC代码: 1 #include

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) B. Batch Sort

链接 题意:输入n,m,表示一个n行m列的矩阵,每一行数字都是1-m,顺序可能是乱的,每一行可以交换任意2个数的位置,并且可以交换任意2列的所有数 问是否可以使每一行严格递增 思路:暴力枚举所有可能的列变换 然后在所有可能的情况下求是否存在一种情况可以使每一行最多进行一次交换最后得到严格递增的矩阵 AC代码: 1 #include "iostream" 2 #include "stdio.h" 3 #include "string.h" 4 us

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) B

Description You are given a table consisting of n rows and m columns. Numbers in each row form a permutation of integers from 1 to m. You are allowed to pick two elements in one row and swap them, but no more than once for each row. Also, no more tha

模拟。。。 Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) C

题目大意:给你一个n*m的矩阵,再给你一个小球,从(0,0)以sqrt(2)/s的速度向右上角出发,遇到边框会反弹,遇到角落就直接停止,给你一些点,问小球第一次经过这些点所需要的时间. 思路:模拟一下即可...注意爆int //看看会不会爆int!数组会不会少了一维! //取物问题一定要小心先手胜利的条件 #include <bits/stdc++.h> using namespace std; #define LL long long #define ALL(a) a.begin(), a.

Intel Code Challenge Final Round (Div. 1 + Div. 2, Combined) E - Goods transportation 最大流转最小割转dp

E - Goods transportation 思路:这个最大流-> 最小割->dp好巧妙哦. #include<bits/stdc++.h> #define LL long long #define fi first #define se second #define mk make_pair #define PII pair<int, int> #define PLI pair<LL, int> #define ull unsigned long lo