hdu 4689 Derangement(dp)
来源:互联网 发布:网络带给我们的坏处 编辑:程序博客网 时间:2024/06/05 06:53
题目链接:hdu 4689 Derangement
解题思路
解法一:枚举二进制状态,为1的位置为满足+,为0的位置为满足-
解法二:dp,dp[i][j][k]表示到第i个位置,前面有j个-被满足,k个+未被满足
代码 - 解法一
#include <cstdio>#include <cstring>#include <algorithm>using namespace std;const int maxn = (1<<20) + 5;typedef unsigned long long ll;int N, K, S, bit[maxn];char str[25];int bitcount(int s) { return s == 0 ? 0 : bitcount(s>>1) + (s&1); }ll add(int s) { int c = 0; ll ret = 1; for (int i = 0; i < N; i++) { if (s&(1<<i)) { if (c == 0) return 0; ret *= c; c--; } if (str[i] == '+') c++; } return ret;}ll del(int s) { int c = 0; ll ret = 1; for (int i = N-1; i >= 0; i--) { if (s&(1<<i)) { if (c == 0) return 0; ret *= c; c--; } if (str[i] == '-') c++; } return ret;}ll solve () { N = strlen(str), K = 0, S = (1<<N)-1; for (int i = 0; i < N; i++) if (str[i] == '+') K++; ll ret = 0; for (int i = 0; i < (1<<N); i++) if (bit[i] == K) { ll l = add(i); if (l == 0) continue; ll r = del(i^S); ret += l * r; } return ret;}int main () { for (int i = 0; i < (1<<20); i++) bit[i] = bitcount(i); while (scanf("%s", str) == 1) { printf("%llu\n", solve()); } return 0;}
代码 - 解法二
#include <cstdio>#include <cstring>#include <algorithm>using namespace std;const int maxn = 25;typedef unsigned long long ll;char str[maxn];ll dp[maxn][maxn][maxn];ll solve () { int n = strlen(str), c = 0; for (int i = 0; i < n; i++) if (str[i] == '-') c++; memset(dp, 0, sizeof(dp)); dp[0][0][0] = 1; for (int i = 0; i < n; i++) { if (str[i] == '+') { for (int x = 0; x < n; x++) { for (int y = 0; y < n; y++) { if (dp[i][x][y] == 0) continue; dp[i+1][x][y+1] += dp[i][x][y]; // 当前位置不变 if (i - x - y > 0) // 和1~i之间满足+的位置交换 dp[i+1][x][y+1] += dp[i][x][y] * (i-x-y); dp[i+1][x][y] += dp[i][x][y] * y; // 和1~i之间不满足+的位置交换 } } } else { for (int x = 0; x < n; x++) { for (int y = 0; y < n; y++) { if (dp[i][x][y] == 0) continue; if (i - x - y > 0) // 和1~i之间满足+的位置交换 dp[i+1][x+1][y] += dp[i][x][y] * (i-x-y); if (y) // 和1~i之间不满足+的位置交换 dp[i+1][x+1][y-1] += dp[i][x][y] * y; } } } } return dp[n][c][0];}int main () { while (scanf("%s", str) == 1) { printf("%llu\n", solve()); } return 0;}
0 0
- hdu 4689 Derangement(dp)
- HDU 4689 Derangement【DP】
- HDOJ 4689 Derangement DP
- HDU 4689 Derangement
- hdu 4689 Derangement
- HDU 4689 Derangement【DP递推】【好题】【思维题】
- HDOJ 4689: Derangement
- GYM 100971 B.Derangement(水~)
- Derangement 问题
- HDU-4689,dp啊!
- HDU 1024(DP)
- HDU 1087(DP)
- HDU 1506(DP)
- hdu 1058 (DP)
- hdu 1208 (DP)
- hdu 4502(DP)
- hdu 4561(DP)
- hdu 1292 (dp)
- Java读取xml文件的四种方法
- ASP.NET多文件上传实例
- Qt从零开始制作串口调试助手-(第四章、新建“串口配置界面”和“关于界面”)-Creator_Ly
- 泛型限定
- 二叉树0607
- hdu 4689 Derangement(dp)
- OpenGL_Qt学习笔记之_04(3D图形的绘制和旋转)
- 排序算法之冒泡排序
- C++设计模式[九]外观模式
- hdu 4691 Front compression(后缀数组)
- Java内存与垃圾回收
- 杭电ACM1114(完全背包)
- 明天面试,大前天离职
- How Many Tables