Number String

Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1016    Accepted Submission(s): 440

Problem Description
The signature of a permutation is a string that is computed as follows: for each pair of consecutive elements of the permutation, write down the letter 'I' (increasing) if the second element is greater than the first one, otherwise write down the letter 'D' (decreasing). For example, the signature of the permutation {3,1,2,7,4,6,5} is "DIIDID".

Your task is as follows: You are given a string describing the signature of many possible permutations, find out how many permutations satisfy this signature.

Note: For any positive integer n, a permutation of n elements is a sequence of length n that contains each of the integers 1 through n exactly once.

 
Input
Each test case consists of a string of 1 to 1000 characters long, containing only the letters 'I', 'D' or '?', representing a permutation signature.

Each test case occupies exactly one single line, without leading or trailing spaces.

Proceed to the end of file. The '?' in these strings can be either 'I' or 'D'.

 
Output
For each test case, print the number of permutations satisfying the signature on a single line. In case the result is too large, print the remainder modulo 1000000007.

 
Sample Input
II
ID
DI
DD
?D
??
 
Sample Output
1
2
2
1
3
6

Hint

Permutation {1,2,3} has signature "II".
Permutations {1,3,2} and {2,3,1} have signature "ID".
Permutations {3,1,2} and {2,1,3} have signature "DI".
Permutation {3,2,1} has signature "DD".
"?D" can be either "ID" or "DD".
"??" gives all possible permutations of length 3.

 
Author
HONG, Qize
 
Source
 
Recommend
lcy
 
题意:
由数字1到n组成的所有排列中,问满足题目所给的n-1个字符的排列有多少个,如果第i字符是‘I’表示排列中的第i-1个数是小于第i个数的。如果是‘D’,则反之。
思路:
首先考虑子问题。设所给模式串长度为i。我们考虑前i-1匹配结尾为j的方法数和长度为i以k结尾的方法数。
我们设dp[i][j]表示前i个位置匹配(即满足条件)且以j结尾的方法数。那么有一个规律。如果前i个位置匹配。对于任意
1<=m<=i。其中x€[m,i]加1后仍匹配。因为大的增幅一致依然大。小的还是小。不过怎么得到递推方程呢?
我们要求dp[i][j]。
1.如果模式串第i位为'I'那么dp[i][j]=segma(dp[i-1][k]).k<j。因为dp[i-1][k]的组合中大于等于j的位置仍满足匹配。而k<j所以可以成功转移。
2.如果模式串第i位为'D'那么dp[i][j]=segma(dp[i-1][k]).k>=j。因为dp[i-1][k]的组合中大于等于j的位置仍满足匹配。而k>=加1后大于j所以可以成功转移。
不过如何保证状态全是dp[i-1]转移来的呢。其实dp[i][j]只是在dp[i-1][k]的基础上增加了一个数i。而把j这个数放到了最后一位而已。而我们用i这个数替换掉j这个数。前面还剩i-1个数。所以dp[i]的状态一定是从dp[i-1]对x€[m,i]加1后转移得到。本来转移有三层循环的不过可以有前缀和优化。用空间换时间了。
详细见代码:
#include <iostream>
#include<stdio.h>
#include<string.h>
using namespace std;
const int maxn=1010;
const int mod=1000000007;
char st[maxn];
int dp[2][maxn],sum[2][maxn]; int main()
{
int i,j,len,v,u; sum[1][0]=sum[0][0]=0;
while(~scanf("%s",st+2))
{
v=0;
len=strlen(st+2);
dp[0][1]=sum[0][1]=1;
for(i=2;i<=len+1;i++)//第一个数前没有数所以从2开始。一直到len+1
{
u=v^1;
for(j=1;j<=i;j++)
{
if(st[i]=='I')
dp[u][j]=sum[v][j-1];
else if(st[i]=='D')
dp[u][j]=(sum[v][i-1]-sum[v][j-1]+mod)%mod;//由于取模可能使大的变小
else
dp[u][j]=sum[v][i-1];
sum[u][j]=(dp[u][j]+sum[u][j-1])%mod;
//printf("sum[%d][%d]:%d\n",i,j,sum[v^1][j]);
}
v=u;
}
printf("%d\n",sum[v][len+1]);
}
return 0;
}

感想:
想了大半个晚上。终于想通点了。DP做着还不是那么顺手。还是题做少了啊。不过我不会放弃的。坚持一定会有效果。加油!


hdu 4055 Number String(有点思维的DP)的更多相关文章

  1. HDU 4055 Number String dp

    题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=4055 Number String Time Limit: 10000/5000 MS (Java/O ...

  2. hdu 4055 Number String (基础dp)

    Number String Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)To ...

  3. hdu 4055 Number String

    Number String http://acm.hdu.edu.cn/showproblem.php?pid=4055 Time Limit: 10000/5000 MS (Java/Others) ...

  4. HDU 4055 Number String:前缀和优化dp【增长趋势——处理重复选数】

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=4055 题意: 给你一个由'I', 'D', '?'组成的字符串,长度为n,代表了一个1~n+1的排列中 ...

  5. hdu 4055 Number String(dp)

    Problem Description The signature of a permutation is a string that is computed as follows: for each ...

  6. HDU 4055 Number String (计数DP)

    题意:由数字1到n组成的所有排列中,问满足题目所给的n-1个字符的排列有多少个,如果第i字符是‘I’表示排列中的第i-1个数是小于第i个数的. 如果是‘D’,则反之. 析:dp[i][j] 表示前 i ...

  7. HDU 4055 Number String(DP计数)

    题意: 给你一个含n个字符的字符串,字符为'D'时表示小于号,字符为“I”时表示大于号,字符为“?”时表示大小于都可以.比如排列 {3, 1, 2, 7, 4, 6, 5} 表示为字符串 DIIDID ...

  8. hdu 4055 Number String(递推DP)

    给一个只含‘I','D','?'三种字符的字符串,I表示当前数字大于前面的数字,D表示当前的数字小于前面一位的数字,?表示当前位既可以小于又可以大于. 问1~n的排列中有多少个满足该字符串. http ...

  9. HDU 4054 Number String

    HDU 4054 Number String 思路: 状态:dp[i][j]表示以j结尾i的排列 状态转移: 如果s[i - 1]是' I ',那么dp[i][j] = dp[i-1][j-1] + ...

随机推荐

  1. 【LeetCode】Repeated DNA Sequences 解题报告

    [题目] All DNA is composed of a series of nucleotides abbreviated as A, C, G, and T, for example: &quo ...

  2. c# 课堂总结6 --集合与结构体

    一.集合 使用时必须添加 System.Collections 集合与数组的区别: 1:数组声明了它容纳的元素的类型,而集合不声明.这是由于集合以object形式来存储它们的元素.初始化时集合无需定义 ...

  3. 【Bootstrap3.0建站笔记一】表单元素排版

    1.文字和输入框前后排列: 代码: <div class="row"> <div class="col-lg-12"> <div ...

  4. wcf 出现 IsContentTypeSupported 错误

    查看添加的服务地址是不是https开头的,而 *.config 文件里面自动添加的链接变成了http,当前的bindbing类型为basicHttpBinding, 解决方法:在config文件里面手 ...

  5. Win32 进程间通信的分析与比较(13种方法)

    1 进程与进程通信 进程是装入内存并准备执行的程序,每个进程都有私有的虚拟地址空间,由代码.数据以及它可利用的系统资源(如文件.管道等)组成.多进程/多线 程是Windows操作系统的一个基本特征.M ...

  6. windows的消息传递--消息盒子(超详细EM_UNDO等消息)

    使用delphi的消息机制可以方便操作后台,其中重要的就是sendmessage()函数.下面讲解一下这个函数 function SendMessage(hWnd: HWND; Msg: UINT;  ...

  7. WCF技术剖析之十九:深度剖析消息编码(Encoding)实现(下篇)

    原文:WCF技术剖析之十九:深度剖析消息编码(Encoding)实现(下篇) [爱心链接:拯救一个25岁身患急性白血病的女孩[内有苏州电视台经济频道<天天山海经>为此录制的节目视频(苏州话 ...

  8. python 读取图片的尺寸、分辨率

    #需要安装PIL模块 #encoding=gbk#--------------------------------------------------------------------------- ...

  9. Use GraceNote SDK in iOS(二)获取音乐的完整信息

    在需求彻底明朗化,外加从MusicFans转到GraceNote,再从GraceNote的GNSDK转到iOS SDK后,最终完毕了在iOS上通过音乐的部分信息获取完整信息的功能了.(好吧,我承认是相 ...

  10. poj3617Best Cow Line

    题意大概是这样,给你一个字符串,你能够进行的操作是这种, 每次拿走这个串的第一个字母,或者最后一个字母,然后放到 一个新串的末尾(当然啦,新串一開始是为空的),当把旧串 里的全部字母拿掉,这个时候就形 ...