点击打开链接

F. AND Graph

time limit per test

4 seconds

memory limit per test

256 megabytes

input

standard input

output

standard output

You are given a set of size m with integer elements between 0 and 2n−1 inclusive. Let's build an undirected graph on these integers in the following way: connect two integers x and y with an edge if and only if x&y=0. Here &is the bitwise AND operation. Count the number of connected components in that graph.

Input

In the first line of input there are two integers nand m (0≤n≤22, 1≤m≤2n).

In the second line there are m

integers a1,a2,…,am ( 0≤ai<2n) — the elements of the set. All ai

are distinct.

Output

Print the number of connected components.

Examples
Input

Copy

2 3
1 2 3

Output

Copy

2

Input

Copy

5 5
5 19 10 20 12

Output

Copy

2

Note

Graph from first sample:

Graph from second sample:

题意:

给出m个大于等于0且小于2^n的不同的整数,如果两个数x&y=0,就把这两个数连接起来,问有多少个连通分支?

错误思路:

并查集,将这m个数两两相与,若x&y=0,则把这两个数放到一个集合,然后标记这m个数的根节点,

最后统计根节点的个数,即连通分支的个数。显然,m非常大时,必定超时

超时代码:

#include<bits/stdc++.h>
using namespace std;
const int maxn=(1<<22)+5;
int fa[maxn];
int find(int x)
{if(fa[x]==x)    return x;return fa[x]=find(fa[x]);
}
void mix(int x,int y)
{int fx=find(x),fy=find(y);fa[fy]=fx;
}
int n,m,a[maxn];
bool vis[maxn];
int main()
{while(scanf("%d%d",&n,&m)!=EOF){bool flag=0;for(int i=0;i<m;i++){scanf("%d",&a[i]);if(a[i]==0)flag=1;}if(flag){printf("1\n");continue;}for(int i=0;i<=(1<<n);i++)fa[i]=i;memset(vis,0,sizeof(vis));for(int i=0;i<m;i++)for(int j=i+1;j<m;j++){if((a[i]&a[j])==0){mix(a[i],a[j]);//printf("%d %d\n",a[i],a[j]);}}for(int i=0;i<m;i++){//printf("%d\n",find(a[i]));vis[find(a[i])]=1;}int ans=0;//for(int i=0;i<=(1<<n);i++)for(int i=0;i<m;i++)if(vis[a[i]])ans++;printf("%d\n",ans);}return 0;
}

正确思路:

x有边连出的一定是 (2^n-1) ^ x 的一个子集,直接连子集复杂度是n^2,但是我们可以一个1一个1的消去,
最后变成补集的一个子集。
但是必须当且仅当 至少有一个 a 等于 x 的时候, 可以直接dfs(all ^ x) ,否则直接消1连边

AC代码:

#include <bits/stdc++.h>using namespace std;
const int maxn = 1<<22;int n, m, a[maxn], all;
int vis[maxn];
int have[maxn];void dfs(int x)
{if(vis[x]) return;vis[x] = 1;if(have[x]) dfs(all ^ x);for(int i = 0;i < n;i ++) {if(x & 1 << i) dfs(x ^ 1 << i);}
}
int main()
{ios::sync_with_stdio(false), cin.tie(0);cin >> n >> m;for(int i = 1;i <= m;i ++) cin >> a[i];for(int i = 1;i <= m;i ++) have[a[i]] = 1;all = 1<<n;all--;int res = 0;for(int i = 1;i <= m;i ++) {if(!vis[a[i]]) {vis[a[i]] = 1;res ++;dfs(all ^ a[i]);}}cout << res << '\n';return 0;
}
正确思路:

对于一个数 11000 则 他必定可以 与 00111相链接, 那么也一定可以和00111中间少了任何几个1的数相连。

任何我们对于任意一个数都跑出他的父亲, 他的父亲就比他多一个1。

如 00001 他的父亲可以为 10001 01001 00101 00011 这4个, 至于 10101 则是 10001(00101)的父亲。

但是,对于一个数来说,他不能直接和他的父节点链接,必须要父节点先和别的数链接,然后子节点就一定可以和父节点链接的那个数链接。

我们先从小到大跑出所有的可以父节点,开另外一个数组去标记。

然后我们从大的数先开始处理,这样我们就会先访问到祖先节点,再访问到子节点,这样可以保证,我们访问到子节点的时候,他的父节点已经处理过了,我们可以得知这2个点是否可以相连接。

对于处理到每一个点,我们先找他的所有父节点,如果可以链接,就直接链接,如果他不能和父节点链接,就去找他的对立节点(即0->1, 1->0),看看这2个点是否可以链接,可以就相连,不可以就将这个节点标记为-1,即没有链接的节点,从而当该节点的子节点访问的时候,就可以得知不能链接。

然后链接的时候用并查集链接块,最后看有几个联通块就是答案了。

#include<bits/stdc++.h>
using namespace std;
const int N = (1<<22) + 100;
bool vis[N], vis1[N];
int pre[N];
int Find(int x){if(x == pre[x]) return x;return pre[x] = Find(pre[x]);
}
int main(){int n, m, t, to, u, v;scanf("%d%d", &n, &m);int Max = (1<<n) - 1;for(int i = 1; i <= m; i++){scanf("%d", &t);vis[t] = 1;}for(int i = 0; i <= Max; i++){vis1[i] |= vis[i];if(vis1[i]) {for(int j = 0; j < n; j++)vis1[i|(1<<j)] = 1;}}bool f = 0;for(int i = 0; i <= Max; i++) pre[i] = i;for(int i = Max; i >= 0; i--){if(!vis1[i]){pre[i] = -1;continue;}f = 0;for(int j = 0; j < n; j++){if(i&(1<<j)) continue;to = i|(1<<j);if(pre[to] != -1){u = Find(i);v = Find(to);pre[u] = v;f = 1;}}if(!f){to = Max ^ i;if(vis1[to]) {u = Find(i);v = Find(to);pre[u] = v;}else pre[i] = -1;}}int ans = 0;for(int i = 0; i <= Max; i++){if(vis[i] && pre[i] == -1) ans++;if(pre[i] == i) ans++;}printf("%d\n", ans);return 0;
}

Codeforces987F AND Graph相关推荐

  1. 图融合GCN(Graph Convolutional Networks)

    图融合GCN(Graph Convolutional Networks) 数据其实是图(graph),图在生活中无处不在,如社交网络,知识图谱,蛋白质结构等.本文介绍GNN(Graph Neural ...

  2. Graph Representation 图神经网络

    Graph Representation 图神经网络 图表示学习(representation learning)--图神经网络框架,主要涉及PyG.DGL.Euler.NeuGraph和AliGra ...

  3. TVM 图优化Graph Optimization

    TVM 图优化Graph Optimization Codegen

  4. ONNX 实时graph优化方法

    ONNX 实时graph优化方法 ONNX实时提供了各种图形优化来提高模型性能.图优化本质上是图级别的转换,从小型图简化和节点消除,到更复杂的节点融合和布局优化. 图形优化根据其复杂性和功能分为几个类 ...

  5. MIT Graph实践概述

    MIT Graph实践概述 Features功能 • iCloud Support • Multi Local & Cloud Graphs • Thread Safe • Store Any ...

  6. list python 转tensor_TensorFlow 中的几个关键概念:Tensor,Operation,Graph,Session

    前言:TensorFlow是一种符号式编程框架,首先要构造一个图(graph),然后在这个图上做运算.打个比方,graph就像一条生产线,session就像生产者.生产线具有一系列的加工步骤(加减乘除 ...

  7. Depth graph

    深度相机 定义:可以直接获取场景中物体距离摄像头物理距离的相机.在计算机视觉系统中,三维场景信息为图像分割.目标检测.物体跟踪等各类计算机视觉应用提供了更多的可能性,而深度图像(Depth map)作 ...

  8. model存数据_Jepsen 测试框架在图数据库 Nebula Graph 中的实践

    在本篇文章中主要介绍图数据库 Nebula Graph 在 Jepsen 这块的实践. Jepsen 简介 Jepsen 是一款用于系统测试的开源软件库,致力于提高分布式数据库.队列.共识系统等的安全 ...

  9. golang通过itemid获取zabbix graph监控图

    2019独角兽企业重金招聘Python工程师标准>>> #简述 本文将使用golang和第三方http client 库gorequest编写.如需要只使用golang 标准库可以参 ...

最新文章

  1. 揭秘鸿蒙系统中的 JS 开发框架
  2. Python语言学习之数值、小数、空格那些事:python和数值、小数、空格的使用方法之详细攻略
  3. eui加载时间长_游戏加载时间越来越短了?背后藏着这些小心机
  4. 使用JDBC,完成对如下表的增删改查操作
  5. Win2003安装后的十个小技巧
  6. 中国电子学会scratch等级考试二级
  7. linux内核那些事之struct page
  8. elementUI组件el-dropdown - 踩坑篇
  9. 声笔码和声笔数码单字效率分析
  10. Nginx配置——禁止指定user_agent
  11. 掌门教育微服务体系 Solar
  12. 用CSS实现立方体360度旋转
  13. 美国会委员会建议禁止中国国企收购美国资产
  14. 如何使用微软提供的TCHAR.H头文件
  15. windows 10上搭建asp网站
  16. IPUS SQPI PSRAM为STM32单片机提供RAM扩展方案
  17. 现货K线图知识之五:北坡炮兵并排跑
  18. 我的学习工作经历,一个园林专业中专毕业生的IT之路 学习编程 创业
  19. C语言再学习25——常用字符串函数归纳
  20. 简介 IndexedDB 及详解 IndexedDB 在实际项目中可能存在的问题与解决方案

热门文章

  1. 为什么要两次调用encodeURI来解决乱码问题
  2. 数据库查找出list数据,进行处理
  3. php汽车配件管理系统,汽配仓库管理系统_汽配库存管理系统
  4. MATLAB已知坐标均匀取电,基于MATLAB带钢卷取电液伺服控制系统的分析(word文档良心出品)(11页)-原创力文档...
  5. python turtle调整画布宽高_turtle.screensize改变不了窗口大小?
  6. zk服务器系统,windows系统搭建zookeeper服务器的教程
  7. 久其通用数据管理平台_银保行业通用的CRM系统,为你轻松化解庞大数据难题
  8. maven打包jar单独配置log4j.properites文件记录日志
  9. 放在每个定义前的html语言,html基础
  10. m227fdw恢复出厂设置_惠普M227fdw使用说明