Bar Codes
| Time Limit: 1000MS | Memory Limit: 10000K | |
| Total Submissions: 917 | Accepted: 323 |
Description
A bar-code symbol consists of alternating dark and light bars, starting with a dark bar on the left. Each bar is a number of units wide. Figure 1 shows a bar-code symbol consisting of 4 bars that extend over 1+2+3+1=7 units.
Figure 1: Bar-code symbol over 7 units (see top) with 4 bars (see bottom)
In general, the bar code BC(n,k,m) is the set of all symbols with k bars that together extend over exactly n units, each bar being at most m units wide. For instance, the symbol in Figure 1 belongs to BC(7,4,3) but not to BC(7,4,2).
Figure 2 shows all 16 symbols in BC(7,4,3). Each `1' represents a dark unit, each `0' a light unit. The symbols appear in lexicographic (dictionary) order. The number on the left of the colon (`:') is the rank of the symbol. The symbol in Figure 1 has rank 4 in BC(7,4,3).
Figure 1: Bar-code symbol over 7 units (see top) with 4 bars (see bottom)
In general, the bar code BC(n,k,m) is the set of all symbols with k bars that together extend over exactly n units, each bar being at most m units wide. For instance, the symbol in Figure 1 belongs to BC(7,4,3) but not to BC(7,4,2).
0: 1000100 | 8: 1100100 1: 1000110 | 9: 1100110 2: 1001000 | 10: 1101000 3: 1001100 | 11: 1101100 4: 1001110 | 12: 1101110 5: 1011000 | 13: 1110010 6: 1011100 | 14: 1110100 7: 1100010 | 15: 1110110 Figure 2: All symbols of BC(7,4,3)
Figure 2 shows all 16 symbols in BC(7,4,3). Each `1' represents a dark unit, each `0' a light unit. The symbols appear in lexicographic (dictionary) order. The number on the left of the colon (`:') is the rank of the symbol. The symbol in Figure 1 has rank 4 in BC(7,4,3).
Input
Your program is to read from standard input. The first line contains the numbers n, k, and m (1 <= n,k,m <= 33). On the second line is a number s (0 <= s <= 100). The following s lines each contain some symbol in BC(n,k,m), represented by '0's and '1's as in
Figure 2.
Output
Your program is to write to standard output. On the first line your program should write the total number of symbols in BC(n,k,m). On each of the s following lines, it should write the rank of the corresponding symbol in the input.
Sample Input
7 4 3 5 1001110 1110110 1001100 1001110 1000100
Sample Output
16 4 15 3 4 0
题意:有n的长度,k个木板,每个木板的长度最多为m,问有多少种组合方式,对于给定的组合是字典序的第多少个。
思路:用dp[i][j]表示后i个木板组成长度为j的有多少种情况。确定给定的组合是第几个的话,就从前往后数,奇数的木板,假如给定的长度为3,那么就答案就加上当它为1和2的时候后面的情况数,偶数的是长度从大到小加上它后面的情况。
AC代码如下:
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
typedef long long ll;
ll dp[40][40];
int num[40];
char s[110];
int n,k,m;
int main()
{
int i,j,a,b,p,cas,pos,len;
ll ans,ret;
while(~scanf("%d%d%d",&n,&k,&m))
{
memset(dp,0,sizeof(dp));
dp[0][0]=1;
for(i=1;i<=k;i++)
for(j=1;j<=n;j++)
{
for(a=1;a<=m && j-a>=0;a++)
dp[i][j]+=dp[i-1][j-a];
}
ans=0;
printf("%I64d\n",dp[k][n]);
scanf("%d",&cas);
while(cas--)
{
scanf("%s",s+1);
pos=0;
for(i=1;i<=k;i++)
{
pos++;
num[i]=1;
while(pos<n && s[pos]==s[pos+1])
{
num[i]++;
pos++;
}
}
len=n;
ans=0;
for(i=k;i>=1;i--)
{
p=k-i+1;
if(p&1)
for(j=1;j<num[p] && len-j>0;j++)
ans+=dp[i-1][len-j];
else
for(j=min(m,len);j>num[p];j--)
ans+=dp[i-1][len-j];
len-=num[p];
}
printf("%I64d\n",ans);
}
}
}

本文探讨了特定条件下条形码符号的组合数量及排列问题,并提供了一种使用动态规划算法来解决该问题的方法。
578

被折叠的 条评论
为什么被折叠?



