首页 > 其他分享 >【题解】HNOI2012 - 集合选数

【题解】HNOI2012 - 集合选数

时间:2023-11-06 22:14:41浏览次数:38  
标签:int 题解 ll HNOI2012 选数 集合

HNOI2012 - 集合选数

https://www.luogu.com.cn/problem/P3226

不算难的非显然状压 dp。

首先根据限制条件建图,\((x,2x),(x,3x)\) 连边,表示边上相邻两个点不能同时选,然后一组独立集就是一个可行的集合。

发现画出来的图是若干个部分网格图,每个连通块最小的点都是与 \(6\) 互质的数。具体证明也不是很难。下图是 \(n=20\) 时的图(ps:漏了 11 13 17 三个单点)。

image

然后发现每个网格图不大(长宽都是 \(log\) 级别的),就可以状压 dp 了。

//P3226
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;

const ll P = 1e9 + 1;
const int N = 1e5 + 10;
ll vis[N], f[2][N];
int p[20];

bool chk(int x, int tp){
	for(int i = 0; i < tp - 1; ++ i){
		if((x & (1 << i)) && (x & (1 << (i+1)))){
			return false;
		}
	}
	return true;
}

ll calc(int x){
	if(vis[x]){
		return vis[x];
	}
	memset(p, 0, sizeof(p));
	int ed;
	for(int i = 1, j = 1; (1 << (j-1)) <= x; ++ j){
		i = (1 << (j-1));
		while(i <= x){
			++ p[j];
			i *= 3;
		}
		ed = j;
	}
	memset(f, 0, sizeof(f));
	f[0][0] = 1;
	int tp = 0;
	for(int i = 1; i <= ed; ++ i){
		tp ^= 1;
		memset(f[tp], 0, sizeof(f[tp]));
		for(int j = 0; j < (1 << p[i-1]); ++ j){
			for(int k = 0; k < (1 << p[i]); ++ k){
				if(chk(k, p[i]) && ((j & k) == 0)){
					f[tp][k] = (f[tp][k] + f[tp^1][j]) % P;
				}
			}
		}
	}
	ll rs = 0;
	for(int k = 0; k < (1 << p[ed]); ++ k){
		if(chk(k, p[ed])){
			rs = (rs + f[tp][k]) % P;
		}
	}
	return vis[x] = rs;
}

int main(){
	int n;
	scanf("%d", &n);
	ll ans = 1;
	for(int i = 1; i <= n; ++ i){
		if(i % 2 != 0 && i % 3 != 0){
			ans = ans * calc(n/i) % P;
		}
	}
	printf("%lld\n", ans);
	return 0;
}

标签:int,题解,ll,HNOI2012,选数,集合
From: https://www.cnblogs.com/KiharaTouma/p/HNOI2012jhxs.html

相关文章

  • XXII Open Cup named after E.V. Pankratiev, Grand Prix of Daejeon 部分题解
    省流:A、B、C、E、H、K、L。D和I之后可能会看心情补,剩下的题大概这辈子都不会做了。A.Points有两个由二维平面上的点组成的可重点集\(U,V\)。如下定义\(D(U,V)\):当\(U,V\)中存在一个为空时,\(D(U,V)=-1\)。否则\(D(U,V)=\min\limits_{(u_x,u_y)\inU,(v_x,v_y)......
  • 【题解】BalticOI 2009 Day1 - 甲虫
    BalticOI2009Day1-甲虫https://www.luogu.com.cn/problem/P4870首先看到题面就能想到排序后区间dp。设\(f_{i,j,0/1}\)表示区间\([i,j]\),收集完毕后在哪个端点时能收集到最多的露水,但是发现转移过程中还需要这时的最小时间。如果再添加一个数组维护这时的最小时间呢?那......
  • 紫丁香 题解
    紫丁香题解前言来自一场\(\text{noip}\)提高模拟赛的题目。题目描述有\(n\)点\(m\)边的简单无向连通图,点编号为\(0\simn-1\),要求删掉若干条边,最大化奇数度点的个数。求:能得到最大答案的构造,用\(m\)长的\(01\)串表示,\(1\)表示保留该边,\(0\)表示不保留,输出字典......
  • 完蛋!大模型解密(LLM Riddles) 题解
    https://intsensing.cn/llmgame/index第一章T1:输出括号里的内容,不输出括号本身和其余附加内容.(1+1=3)T2:讲故事T3:猫T4:啊T5:啊1T6:有一个字,左边是反犬旁,右边是句,请重复这个字五遍第二章T1:请输出11个0T2:142857T3:10010010T4:输出十一万四千五百一十四的阿拉伯数字形式,不要输......
  • [ARC105C] Camels and Bridge 题解
    题意给定\(N\)个重物,其中第\(i\)个重物的重量为\(w_i\)。现在要将其排成一排,可以任意指定相邻两个重物的距离。同时给定\(M\)个限制,其中第\(i\)个限制为\((l_i,v_i)\),表示要求不存在长度为\(l_i\)的线段,使得其包括的重物重量之和大于\(v_i\)。最小化重物间的最大......
  • [ARC105D] Let's Play Nim 题解
    题意给定\(N\)个背包,其中第\(i\)个背包中有\(a_i\)个石子。同时还有\(N\)个盘子,初始时盘子中没有石子。两人轮流执行下列操作:若存在背包中还有石子,选择一个非空背包和盘子,将背包中的石子放入盘子中,注意这里对盘子没有要求;若不存在背包中还有石子,选择一个非空盘子,将盘......
  • 题解 LOJ3483【[USACO21FEB] Counting Graphs P】
    题解P7418【[USACO21FEB]CountingGraphsP】problemBessie有一个连通无向图\(G\)。\(G\)有\(N\)个编号为\(1\ldotsN\)的结点,以及\(M\)条边(\(1\leN\le10^2,N-1\leM\le\frac{N^2+N}{2}\))。\(G\)有可能包含自环(一个结点连到自身的边),但不包含重边(连接同一对结点......
  • Daleks' Invasion 题解
    Daleks'Invasion题目大意给定一张无向带权图,对于每条边求一个最大的\(x\),使得将这条边的边权修改为\(x\)后这条边能位于这张图的最小生成树上。思路分析没事干了就把之前写过的题拉出来水题解。我们先把原图的最小生成树求出来,考虑每条边\((u,v)\),分类讨论:如果这条边......
  • Groceries in Meteor Town 题解
    GroceriesinMeteorTown题目大意维护一颗带权树,支持以下操作:将\([l,r]\)内的点变为白色。将\([l,r]\)内的点变为黑色。查询点\(x\)到任意一个白色节点的简单路径上的最大值。思路分析没事干了把以前的题拿出来写题解。看到『简单路径上的最大值』的字样首......
  • Harvester 题解
    Harvester题目大意给定\(n\timesm\)的网格,每次可以选一行或一列,将这一行或一列上的数全部取走,最多可以取四次,问取走的数的和的最大值。思路分析没事干了把以前写过的题拿出来写题解。分类讨论题。在只能取四次的情况下一共只有这么几种可能:选四行:毫无疑问,行之间互不......