题目描述:

我们给出 S,一个源于 {'D', 'I'} 的长度为 n 的字符串 。(这些字母代表 “减少” 和 “增加”。)
有效排列 是对整数 {0, 1, ..., n} 的一个排列 P[0], P[1], ..., P[n],使得对所有的 i:

如果 S[i] == 'D',那么 P[i] > P[i+1],以及;
如果 S[i] == 'I',那么 P[i] < P[i+1]。
有多少个有效排列?因为答案可能很大,所以请返回你的答案模 10^9 + 7.

示例:

输入:"DID"
输出:5
解释:
(0, 1, 2, 3) 的五个有效排列是:
(1, 0, 3, 2)
(2, 0, 3, 1)
(2, 1, 3, 0)
(3, 0, 2, 1)
(3, 1, 2, 0)

提示:

  1. 1 <= S.length <= 200
  2. S 仅由集合 {'D', 'I'} 中的字符组成。

思路分析:

我们用 dp(i, j) 表示确定了排列中到 P[i] 为止的前 i + 1 个元素,并且 P[i] 和未选择元素的相对大小为 j 的方案数(即未选择的元素中,有 j 个元素比 P[i] 小)。在状态转移时,dp(i, j) 会从 dp(i - 1, k) 转移而来,其中 k 代表了 P[i - 1] 的相对大小。如果 S[i - 1] 为 D,那么 k 不比 j 小;如果 S[i - 1] 为 I,那么 k 必须比 j 小。

代码:

 class Solution {
public:
int mod = 1e9+;
int numPermsDISequence(string S) {
int n = S.size();
if(n==)
return ;
vector<vector<int>> dp(n+, vector<int>(n+, ));
for(int i=; i<n+; i++)
dp[][i]=;
for(int i=; i<=n; i++)
{
for(int j=; j<=i; j++)
{
if(S[i-]=='D')
{
for(int k=j; k<i; k++)
{
dp[i][j] += dp[i-][k];
dp[i][j] %= mod;
}
}
else
{
for(int k=; k<j; k++)
{
dp[i][j] += dp[i-][k];
dp[i][j] %= mod;
}
}
}
}
int ans = ;
for(int i=; i<=n; i++)
{
ans += dp[n][i];
ans %= mod;
}
return ans;
}
};

最新文章

  1. iOS Hit-Test应用
  2. 【重装系统】线上Linux服务器(2TB)分区参考方案
  3. 分享google的技能的11个级别,大家看看自己到哪个级别了?
  4. ASP.NET MVC动态生成网站菜单及子菜单
  5. Hibernate的ORM原理和实现
  6. 火狐插件 Http请求利器 Httprequester
  7. Java线程池与java.util.concurrent
  8. Spark Standalone运行过程
  9. Android Camera
  10. 在treeview外加一个滚动条的实现
  11. Object lifetime
  12. python——爬虫&amp;问题解决&amp;思考(三)
  13. 再谈前端HTML模板技术
  14. SublimeText3追踪函数工具CTags设置及使用
  15. 使用canvas实现一个圆球的触壁反弹
  16. 一套oracle的练习题
  17. svn 更新提交文件冲突
  18. Filter过滤器原理和登录实现
  19. java:从消息机制谈到观察者模式
  20. mysql之InnoDB内存管理

热门文章

  1. MySQL5.7安装脚本
  2. Entity Framework 导航属性(2)
  3. pycharm工具设置py模板
  4. jmeter入门操作 = 录制
  5. maven 学习---Maven快照
  6. Android探索之百度地图开发
  7. vuejs的导航栏固定
  8. apache主配置文件设置
  9. Spring(003)-消费返回list的rest服务
  10. 201871010109-胡欢欢《面向对象程序设计(java)》第十周学习总结