原文链接https://www.cnblogs.com/cly-none/p/9695526.html

题意:求有多少对集合\(S,T\)满足:\(S \subseteq \{1,2...n \}, T \subseteq \{1,2...m\},S \bigcap T = \emptyset\),且\(S\)中所有元素的异或和小于\(T\)中所有元素的异或和。对\(10^9+7\)取模。

\(n,m \leq 2000\)

首先,通过记录当前两个集合的异或和,转移时考虑每个元素的3种选择,容易得到\(O(n^3)\)的暴力dp。然而,要对此优化却是一件困难的事情。

但无论如何,对状态的优化的必要的。因此,我们就必须避免同时记录两个集合的异或和。考虑两个异或和如果只有一位,那么它们的大小关系就能通过记录一位来得到。而对于多位的二进制数的大小比较,我们也只用比较不同的最高位就可以了。

因此,我们枚举不同的最高位。那么,我们就可以忽略后面的位,并只用记录我们所枚举的这一位。剩下的问题就在于保证更高的位是相等的。那可以用记录两个数在更高位上的异或和实现,异或和为0,这两个数就是相等的。

时间复杂度\(O(n^2\log n)\)。

upd18.9.25

确实如zhouzhendong所说,这是\(O(n^2)\)的。下面代码已修改。

#include <bits/stdc++.h>
using namespace std; const int N = 2060, MOD = (int)(1e9 + 7);
int dp[N][N][2],n,m,len,ans; class WinterAndSnowmen {
public:
int getNumber( int N, int M );
};
int WinterAndSnowmen::getNumber(int N, int M) {
n = N, m = M;
len = max(n,m);
for (int s = 1 ; s <= 12 ; ++ s) {
memset(dp,0,sizeof dp);
dp[0][0][0] = 1;
for (register int i = 1 ; i <= len ; ++ i) {
for (register int j = 0 ; j < (2048 >> (s-1)) ; ++ j) {
for (int k = 0 ; k < 2 ; ++ k) {
if (i <= n)
(dp[i][j^(i>>(s-1))][k] += dp[i-1][j][k]) %= MOD;
if (i <= m)
(dp[i][j^(i>>(s-1))][k ^ ((i >> (s-1))&1)] += dp[i-1][j][k]) %= MOD;
(dp[i][j][k] += dp[i-1][j][k]) %= MOD;
}
}
}
(ans += dp[len][1][1]) %= MOD;
}
return ans;
}

小结:虽然是“思维训练”中的题,但也会有自己没有掌握的技巧。

【做题】TCSRM601 Div1 500 WinterAndSnowmen——按位考虑&dp的更多相关文章

  1. 【做题】arc078_f-Mole and Abandoned Mine——状压dp

    题意:给出一个\(n\)个结点的联通无向图,每条边都有边权.令删去一条边的费用为这条边的边权.求最小的费用以删去某些边使得结点\(1\)至结点\(n\)有且只有一条路径. \(n \leq 15\) ...

  2. 【做题】spoj4060 A game with probability——dp

    赛前做题时忽然发现自己概率博弈类dp很弱,心好慌.(获胜概率或最优解期望) 于是就做了这道题,续了特别久. 一开始列dp式子的时候就花了很长时间,首先搞错了两次,然后忘记了根据上一轮dp值直接确定选什 ...

  3. bzoj5108 [CodePlus2017]可做题 位运算dp+离散

    [CodePlus2017]可做题 Time Limit: 10 Sec  Memory Limit: 512 MBSubmit: 87  Solved: 63[Submit][Status][Dis ...

  4. CodeM美团点评编程大赛复赛 做题感悟&题解

    [T1] [简要题意]   长度为N的括号序列,随机确定括号的方向:对于一个已确定的序列,每次消除相邻的左右括号(右左不行),消除后可以进一步合并和消除直到不能消为止.求剩下的括号的期望.\(N \l ...

  5. TopCoder SRM502 Div1 500 贪心 01背包

    原文链接https://www.cnblogs.com/zhouzhendong/p/SRM502-500.html SRM502 Div1 500 好题. 首先,如果已经确定了解决所有问题的优先级, ...

  6. SAM 做题笔记(各种技巧,持续更新,SA)

    SAM 感性瞎扯. 这里是 SAM 做题笔记. 本来是在一篇随笔里面,然后 Latex 太多加载不过来就分成了两篇. 标 * 的是推荐一做的题目. trick 是我总结的技巧. I. P3804 [模 ...

  7. C语言程序设计做题笔记之C语言基础知识(下)

    C 语言是一种功能强大.简洁的计算机语言,通过它可以编写程序,指挥计算机完成指定的任务.我们可以利用C语言创建程序(即一组指令),并让计算机依指令行 事.并且C是相当灵活的,用于执行计算机程序能完成的 ...

  8. C语言程序设计做题笔记之C语言基础知识(上)

    C语言是一种功能强大.简洁的计算机语言,通过它可以编写程序,指挥计算机完成指定的任务.我们可以利用C语言创建程序(即一组指令),并让计算机依指令行事.并且C是相当灵活的,用于执行计算机程序能完成的几乎 ...

  9. bzoj5108: [CodePlus2017]可做题

    Description qmqmqm希望给sublinekelzrip出一道可做题.于是他想到了这么一道题目:给一个长度为n的非负整数序列ai,你需 要计算其异或前缀和bi,满足条件b1=a1,bi= ...

随机推荐

  1. Springboot杂七杂八

    1 加载配置文件 private static ResourceBundle resb = ResourceBundle.getBundle("serverInfo"); 然后在r ...

  2. mysql 问题:wait_timeout

    1,show global variables like 'wait_timeout'; 查询'wait_timeout' 默认是8天即28800秒 2,修改 windows 安装目录下的my.ini ...

  3. 20165305 Linux安装及学习

    一.虚拟机的安装 在根据老师所给的<基于VirtualBox虚拟机安装Ubuntu图文教程>的时候,我发现虚拟化处于被禁用状态,于是我在网上查找了一下解决办法,在我将bios中虚拟化设置为 ...

  4. hive中的with用法

    hive 可以通过with查询来提高查询性能,因为先通过with语法将数据查询到内存,然后后面其它查询可以直接使用,这种方法与创建临时表类似但是不需要创建临时表实体表,内存中的子查询结果在会话结束后会 ...

  5. 转:C# 使用资源文件 Resource.resx 的方法

    在写程序时, 可以把用到的 图标,图片,声音等外部资源,放在一个  .resx (资源文件)中. 这样的好处是不用考虑什么路径的问题.而且还对资源有保护的做用. 1.创建一个 ResourceFile ...

  6. Linux shell 时间操作(取昨天 前天)

    1. 取今天时间 $date -d "now" +%Y-%m-%d 2. 取昨天时间 $date -d "yesterday" +%Y-%m-%d $date  ...

  7. 在centos上搭建Git服务器

    第一步:先安装一些相关依赖库和编译工具 yum install curl-devel expat-devel gettext-devel openssl-devel zlib-devel yum in ...

  8. node.js基本使用

    1.引入http模块(node的核心模块) const http = require("http"); 2.createServer来创建服务器 http.createServer ...

  9. Python进阶【第六篇】内置函数中好玩的几个(今天写的太水)

    zip()函数 两个参数一一对应,参数是序列类型,序列包括列表,元组,字符串,当两个序列不等长时,按公共最长部分匹配,形似“拉链”. max()和min()函数 以max()为例,min()类似,只是 ...

  10. mysql日志种类、二进制日志模式、mysqlbinlog解析二进制日志

    mysql日志的种类 二进制日志(binary log):记录数据更新的操作,mysqlbinlog 可查看二进制日志文件 错误日志(error log):记录mysql服务进程mysqld的启动.关 ...