[USACO3.2]01串 Stringsobits
来源:互联网 发布:济南行知小学怎么样 编辑:程序博客网 时间:2024/06/08 11:24
题目背景
考虑排好序的N(N<=31)位二进制数。
题目描述
他们是排列好的,而且包含所有长度为N且这个二进制数中1的位数的个数小于等于L(L<=N)的数。
你的任务是输出第i(1<=i<=长度为N的二进制数的个数)小的(注:题目这里表述不清,实际是,从最小的往大的数,数到第i个符合条件的,这个意思),长度为N,且1的位数的个数小于等于L的那个二进制数。
(例:100101中,N=6,含有位数为1的个数为3)。
输入输出格式
输入格式:共一行,用空格分开的三个整数N,L,i。
输出格式:共一行,输出满足条件的第i小的二进制数。
输入输出样例
5 3 19
10011
说明
题目翻译来自NOCOW。
USACO Training Section 3.2
【题解】
d[i][j]表示长度为i,1的个数至多为j的二进制数量
边界:d[i][0]=1;(任何位没有至多0个1的情况只有一种0000000....)d[0][i]=1;(主要是为了在递推的过程中,长度为1,1个数至多j的二进制转移正确。(长度为1的情况下,只有0,1两种))
d[i][j]=d[i-1][j]+d[i-1][j-1]分别有第i位为1,0两种情况。//前者是第i位为0的情况下,后者为第i位为1的情况
打印解得原理:
有转移方程可以知道,I>d[i-1][L]的情况时候,必定存在d[i-1][j-1]的情况,此时我们确定第i位必定为1,所以减去第i位为0,长度为i的情况 剩下的就是第i位为1的情况
比如找3位,1个数不超过3个,的第7个二进制 数
000
001
010
011
减掉上面的 ,第三位为0的情况 剩下的是:
100
101
110
111
减去的上面部分 7-4=3;剩下4种第3位为1的情况,则下面讨论的其实是:
00
01
10
11
转移到这了 重复这样的步骤(求2位,1个数不超过3-1=2个,第3位二进制数),就能确定第2位第1位了
看了题解,不详细┭┮﹏┭┮没想到自己模拟下就想通了,把原本题解翻译成人能听懂的话,(逃
想了一天,也算有收获..动态规划可以这样玩。。
/*ID:luojiny1LANG:C++TASK:kimbits*/#include<cstdio>int d[35][35] = { 0 }, ans[35]; int main(){freopen("kimbits.in","r",stdin);freopen("kimbits.out","w",stdout); int N, L;long long I;scanf("%d%d%lld", &N, &L, &I);for (int i = 0; i <= N; i++)d[i][0] =d[0][i]=1;for (int i = 1; i<=N; i++)for (int j = 1; j <= N; j++)if(j<=i)d[i][j] = d[i - 1][j - 1] + d[i - 1][j];else d[i][j] = d[i][i];for (int i = N; i >= 1; i--) {if (I > d[i - 1][L]) {putchar('1');I -= d[i - 1][L];L--;}else putchar('0');}putchar('\n');return 0;}
以下是模拟算法(78~90分):
/*ID:luojiny1LANG:C++TASK:kimbits*/#include<cstdio>#include<bitset>#include<iostream>using namespace std;long long BitCount(long long n){ n=(n&0x5555555555555555LL)+((n>>1)&0x5555555555555555LL); n=(n&0x3333333333333333LL)+((n>>2)&0x3333333333333333LL); n=(n&0x0F0F0F0F0F0F0F0FLL)+((n>>4)&0x0F0F0F0F0F0F0F0FLL); n=(n&0x00FF00FF00FF00FFLL)+((n>>8)&0x00FF00FF00FF00FFLL); n=(n&0x0000FFFF0000FFFFLL)+((n>>16)&0x0000FFFF0000FFFFLL); n=(n&0x00000000FFFFFFFFLL)+((n>>32)&0x00000000FFFFFFFFLL); return n;}int main(){// freopen("kimbits.in","r",stdin);// freopen("kimbits.out","w",stdout); unsigned int N,I,L; scanf("%u%u%u",&N,&L,&I); unsigned int i=0,maxI=1<<N,j=0,last=0; for(;i<maxI&&j<I;i++){ int cnt=BitCount(i); if(cnt<=L){ j++; last=i; } } bitset<33>BIT(last); for(int i=N-1;i>=0;i--)cout<<BIT[i]; cout<<endl; return 0;}
- [USACO3.2]01串 Stringsobits
- [luogu2727][USACO3.2]Stringsobits(dp)
- USACO3.2.2 Stringsobits (kimbits)
- USACO3.2.2 Stringsobits (kimbits)
- usaco3.2.2 Stringsobits
- usaco 01串 Stringsobits
- USACO Training 3.2.2 Stringsobits 01串 题解与分析
- usaco3.2.3 01串
- 【USACO3.2.2】01串
- 【C++】【USACO3.2.2】01串
- USACO 3.2.2 stringsobits
- USACO 3.2.2 Stringsobits
- USACO 3.2.2:Stringsobits
- stringsobits
- Stringsobits
- usaco3.2kimbits
- USACO3.2--Spinning Wheels
- [USACO3.2]阶乘 Factorials
- GCD栅栏
- 【数据库系统概念】第7章 数据库设计和E-R模型 知识总结
- Agglomerative Hierarchical Clustering(AHC)
- Android 测试
- HTML常用的jquery操作-yellowcong
- [USACO3.2]01串 Stringsobits
- Servlet容器与Web容器
- NYOJ 5 Binary String Matching
- 基于以太坊系统的货币系统(一)
- PHP 表单和用户输入方法
- 国内8款热门协作软件综合比较
- apt-get update 神奇的不灵了
- JS三元运算符
- mpeg4ip.h:126: error: new declaration ‘char* strcasestr(const char*, const char*)’