当前位置: 首页 > news >正文

线性基速通

1. 引入线性基的问题:
  • 一些数随意选取,求可以异或出的第k大数。单纯枚举所有情况的话是 O ( 2 n ) O(2^n) O(2n),引入线性基后,可以把时间复杂度降低到 O ( n l o g n ) O(nlogn) O(nlogn)
2. 什么是线性基&&为什么线性基可以降低时间复杂度:
  • 把一堆数以二进制的形式纵向排列,形成了 n ∗ 64 n*64 n64 01 01 01 矩阵,由于矩阵的秩 r ( A ) ≤ m i n ( n , 64 ) r(A)\leq min(n,64) r(A)min(n,64)
  • 可以证明这些数字组成的矩阵一定可以找到大小小于等于 64 64 64 Z 2 {Z}_2 Z2 域中的线性无关组。( 在 Z 2 {Z}_2 Z2 中的加法为异或,乘法为与,可以证明 Z 2 {Z}_2 Z2 是域。)
  • 找到线性无关组之后,一个简单的想法就是枚举所有向量的组合,实际上起作用的向量只有64个, O ( 2 64 ) O(2^{64}) O(264) 就可以找到所有的情况了,这样的线性无关组就是线性基。实际上,如果只需要寻找一个数可不可以被构成,可以达到 O ( l o g n ) O(logn) O(logn) 的级别。
3. 如何实现寻找线性基等函数
  • 贪心构造出向量组的线性基:
    void insert(int x){//插入一个数xfor(int i=63;i>=0;i--){if(x&(1ll<<i)){if(p[i]) x^=p[i];else {p[i]^=x;cnt++;break;}}}
    }
    
    贪心地选取每一位,如果这一位已经有了,就把它异或掉,可以证明到最后一定是一组基。
    这样构造出来的线性基, p [ i ] p[i] p[i] 一定是表示首位为 1 1 1 的基,而且不会重复,插入单个元素复杂度 O ( l o g n ) O(logn) O(logn)
  • 寻找最大数:
    int askmx(){int x=0;for(int i=63;i>=0;i--){if((x^p[i])>x) x^=p[i];}return x;
    }
    
    从高位到低位枚举,贪心选取最高位一定是对的。
  • 寻找最小数:
      int askmn(){int mn=inf;if(cnt==0||n>cnt) return 0;else{for(int i=0;i<=64;i++){if(p[i]) mn=min(mn,p[i]);}return mn;}}
    
    一般来说,最小值就是贪心构造出来的线性基的某个值,但是需要考虑一个特殊情况——几个数异或起来变成了 0 0 0。这种情况只需要判断插入的数字的数量和这些数字构造出的基的数量,如果有数字没有成为基,那么它一定可以被其它基线性表出,这种情况会异或出0。
  • 查询是否可以构造出某个数:
    bool ask(int x){//查询是否有一个数字for(int i=63;i>=0;i--){if(x&(1ll<<i)){if(p[i]) x^=p[i];}}return (x==0);
    }
    
    从大到小异或,这样如果最后异或为 0 0 0,代表可以线性表出,不为零代表不行。
  • 求第 k k k 大数:
    void rebuild() {cnt=0;for(int i=63;i>=0;i--)for(int j=i-1;j>=0;j--)if(p[i]&(1LL<<j)) p[i]^=p[j];for(int i=0;i<=63;i++) if(p[i]) d[cnt++]=p[i];
    }
    int kth(int k) {if(k>=(1LL<<cnt)) return -1;int ans=0;for(int i=63;i>=0;i--)if(k&(1LL<<i)) ans^=d[i];return ans; 
    }
    
    原来的线性基不满足求第 k k k 大的要求,不满足行阶梯型,即不会有两个线性基共享其中一个的最高位,如 10110 10110 10110 00100 00100 00100 ,不是一组完美的线性基。需要通过高斯消元求阶梯形。
    求完之后,可以直接贪心选取第k个数。
    这里还需要判断 0 0 0 的情况,如果会凑出 0 0 0 ,查询位置要递推 1 1 1
    for(int i=0;i<64;i++) p[i]=0;
    int n;cin>>n;
    for(int i=1;i<=n;i++){int x;cin>>x;insert(x);
    }
    rebuild();
    int m;cin>>m;
    if(n>cnt) zero=1;
    for(int i=1;i<=m;i++){int q;cin>>q;if(n>cnt&&q==1) cout<<0<<endl;else cout<<kth(q-zero)<<endl;
    }
    
4. 线性基一些性质:
  • Q: 有 n n n 个元素,每个元素有个序号和一个值,一个元素可以选择当且尽当其序号与已选元素序号的异或和不为 0 0 0,求你可选择的元素值和的最大值
  • A: 贪心地将最大值元素的序号塞入线性基中,如果插入失败,就不选择这个元素。这样插入的结果一定是最大值。
  • 性质:如果一个元素不能插入线性基中(可以被其它线性基线性表出),一定可以只删掉一个元素,把它插入线性基。
5. 一道测试题:
  • https://codeforces.com/gym/105336/attachments
  • a i a_i ai b i b_i bi 的值异或起来,插入线性基,然后按位分类讨论贪心即可。

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 【STM32】独立看门狗(IWDG)原理详解及编程实践(上)
  • OpenCV-模板匹配多个目标
  • 【Java】网络编程:TCP_IP协议详解(IP协议数据报文及如何解决IPv4不够的状况)
  • React学习day07-ReactRouter-抽象路由模块、路由导航、路由导航传参、嵌套路由、默认二级路由的设置、两种路由模式
  • Java多线程面试精讲:源于技术书籍的深度解读
  • Python中 BeautifulSoup和Selenium 定位元素和获取元素值的方法
  • 基于Jeecgboot3.6.3的flowable流程增加任务节点字段的控制(一)
  • 代理导致的git错误
  • 【STM32 Blue Pill编程】-定时器PWM模式
  • 系统架构设计师:软件架构的演化和维护
  • Qt自动打开文件夹并高亮文件
  • Java中的正则表达式
  • Vue.js: 构建动态用户界面的现代框架
  • C# 使用Socket通信,新建WinForm服务端、客户端程序
  • 使用 Nmap 进行 SSL/TLS 加密套件枚举
  • 【译】JS基础算法脚本:字符串结尾
  • [rust! #004] [译] Rust 的内置 Traits, 使用场景, 方式, 和原因
  • 【node学习】协程
  • 2018以太坊智能合约编程语言solidity的最佳IDEs
  • 345-反转字符串中的元音字母
  • Asm.js的简单介绍
  • el-input获取焦点 input输入框为空时高亮 el-input值非法时
  • fetch 从初识到应用
  • js递归,无限分级树形折叠菜单
  • mysql 5.6 原生Online DDL解析
  • 初识 webpack
  • 纯 javascript 半自动式下滑一定高度,导航栏固定
  • 给github项目添加CI badge
  • 诡异!React stopPropagation失灵
  • 基于Mobx的多页面小程序的全局共享状态管理实践
  • 聊聊sentinel的DegradeSlot
  • 让你的分享飞起来——极光推出社会化分享组件
  • 山寨一个 Promise
  • kubernetes资源对象--ingress
  • ​Linux Ubuntu环境下使用docker构建spark运行环境(超级详细)
  • ​ubuntu下安装kvm虚拟机
  • ​探讨元宇宙和VR虚拟现实之间的区别​
  • # Panda3d 碰撞检测系统介绍
  • #{}和${}的区别是什么 -- java面试
  • %@ page import=%的用法
  • ( )的作用是将计算机中的信息传送给用户,计算机应用基础 吉大15春学期《计算机应用基础》在线作业二及答案...
  • (2)关于RabbitMq 的 Topic Exchange 主题交换机
  • (不用互三)AI绘画工具应该如何选择
  • (附源码)c#+winform实现远程开机(广域网可用)
  • (附源码)计算机毕业设计SSM在线影视购票系统
  • (计算机网络)物理层
  • (剑指Offer)面试题41:和为s的连续正数序列
  • (蓝桥杯每日一题)love
  • (南京观海微电子)——I3C协议介绍
  • (三)Kafka 监控之 Streams 监控(Streams Monitoring)和其他
  • (推荐)叮当——中文语音对话机器人
  • (源码分析)springsecurity认证授权
  • (轉貼) 寄發紅帖基本原則(教育部禮儀司頒布) (雜項)
  • .NET 5种线程安全集合
  • .NET delegate 委托 、 Event 事件