题目

给出两个正整数N和M, N <= 100, M <= 50, 可以将N分解成若干个不相等的正整数A1, A2... Ak的和,且A1, A2 ... Ak的乘积为M的倍数。即 
N = A1 + A2 + ... + Ak; 
A1*A2*...Ak % M = 0; 
求可以有多少种分解方式? 
题目链接: divided product

分析

直接DFS搜索,DFS(cur_sum, cur_max_num, cur_product) 枚举出总和为N的,且各个数字不断增加的方案,然后判断他们的乘积是否等于M的倍数。实现复杂度为:(2^t, t 为几十的量级),显然不行; 
考虑动态规划来解决: 
    维护状态 dp[i][j][t] 表示 A1,A2...Ak的总和为i,且最大的数字Ak等于j,A1*A2..A*k的结果模M为t的分解方案总个数。 
则可以有递推公式:

  1. int tt = k*t%M;
  2. dp[i + k][k][tt] += dp[i][j][t];
  3. dp[i + k][k][tt] %= mod;

其中需要注意 边界条件 dp[i][i][i%M] = 1.

实现

#include<stdio.h>
#include<string.h>
#include<iostream>
#include<string>
#include<set>
#include<map>
#include<vector>
#include<queue>
#include<stack>
#include<unordered_map>
#include<unordered_set>
#include<algorithm>
using namespace std;
int dp[105][105][55];
int main(){
const int mod = 1000000007;
int n, m;
scanf("%d %d", &n, &m);
memset(dp, 0, sizeof(dp));
for (int i = 0; i <= n; i++){
for (int j = 0; j <= i; j++){
for (int k = j + 1; (k + i) <= n; k++){
for (int t = 0; t < m; t++){
if (i == 0)
dp[k][k][k%m] = 1;
else{
int tt = k*t%m;
dp[i + k][k][tt] += dp[i][j][t];
dp[i + k][k][tt] %= mod;
}
}
}
}
}
int result = 0;
for (int i = 1; i <= n; i++)
result = (result + dp[n][i][0]) % mod;
printf("%d\n", result);
return 0;
}

hiho1096_divided_product的更多相关文章

随机推荐

  1. java 导入自定义类

    eclipse导入很容易,昨天上课学了一下用记事本写java,导入自定义类,这就麻烦了. 代码贴一下,方便操作: package tom.jiafei; public class SquareEqua ...

  2. 第十四章:高级I/O

    14.1:引言 本章内容包括非阻塞I/O.记录锁.系统V流机制.I/O多路转接(select和poll函数).readv和writev函数以及存储映射I/O(mmap),这些都称为高级I/O. 14. ...

  3. hdu So Easy!

    So Easy! Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total Su ...

  4. #ifdef DEBUG的理解

    今天看到一段代码,对ifdef的概念比较模糊,于是去学习了一下,找到一个很好的解释,如下: 在工程设置里有一些设置会对该工程自动产生一系列的宏,用以控制程序的编译和运行.就好象楼上说的一样,如果你把代 ...

  5. sql 清空所有数据

    近来发现数据库过大,空间不足,因此打算将数据库的数据进行全面的清理,但表非常多,一张一张的清空,实在麻烦,因此就想利用SQL语句一次清空所有数据.找到了三种方法进行清空.使用的数据库为MS SQL S ...

  6. Android BroadcastReceiver广播接受者

    静态注册 配置清单表注册:只要曾经注册过哪怕关闭也能调用  方式一:sendBroadCastReceive   广播的步骤:       发送  无序广播,普通广播       (1).发送方    ...

  7. centos Linux 统计某个文件夹占用空间大小

    转载自 http://www.07net01.com/linux/centos_Linux_tongjimougewenjianjiazhanyongkongjiandaxiao_12510_1346 ...

  8. SqlSever基础 datepart 获取一个日期的年份

    镇场诗:---大梦谁觉,水月中建博客.百千磨难,才知世事无常.---今持佛语,技术无量愿学.愿尽所学,铸一良心博客.------------------------------------------ ...

  9. SqlSever基础 intersect 交集 两个查询结果共有的

    镇场诗:---大梦谁觉,水月中建博客.百千磨难,才知世事无常.---今持佛语,技术无量愿学.愿尽所学,铸一良心博客.------------------------------------------ ...

  10. 【leetcode❤python】198. House Robber

    class Solution(object):    def rob(self, nums):        """        :type nums: List[in ...