动态规划_二项式系数

动态规划之二项式系数

@(算法学习)

(nk)=n!(n?k)!k!

计算二项式系数的问题在于,系数本身在int表示范围内,但是计算用到的分子是阶乘,这个是很大的数,会导致溢出的问题。

所以,比较好的计算方法是运用帕斯卡三角形总结的规律求解。

第一行表达的是:(00)=1

第二行表达的是:(10)=1,(11)=1

第三行表达的是:(20)=1,(21)=2,(22)=1

更有趣的是,每一个数是肩头两个数字之和。

运用的规律是:(nk)=(n?1k?1)+(n?1k)

,这个翻译成中文很好理解。从n个东西中选取k个,在面对第k件东西时,有一个决策,这件不选或者选两条路径。选了第k件则从剩下的n-1件里选k-1件即可。如果不选,就要从剩下的n-1件中选择k件。

这个思想在背包问题中运用的尤其广泛。背包问题是动态规划问题的一种模型,因此,也可以侧面反映动态规划的思想。

#include <stdio.h>

#define MAXN 100

long binomial_coefficient(int n, int m)// 从n中选择m
{
    int i,j;
    long bc[MAXN][MAXN]; //二项式系数表
    for(i = 0; i <= n; i++) //帕斯卡三角每行第一个数全是1
    {
        bc[i][0] = 1;
    }
    for(j = 0; j <= n; j++) // 帕斯卡三角每行最后一个数全是1
    {
        bc[j][j] = 1;
    }

    for(i = 1; i <= n; i++) //状态转移方程
    {
        for(j = 1; j < i; j++)
        {
            bc[i][j] = bc[i-1][j-1]+bc[i-1][j];
        }
    }
    return bc[n][m];
}
int main()
{
    int n, m;
    while(scanf("%d%d",&n,&m))
    {
        int res = binomial_coefficient(n,m);
        printf("Result =  %d\n", res);
    }

    return 0;
}

原文地址:https://www.cnblogs.com/passion-sky/p/9193163.html

时间: 2024-10-08 15:16:44

动态规划_二项式系数的相关文章

动态规划 — 计算二项式系数

如果问题是由交叠的子问题所构成的,那么我们就可以用动态规划技术来解决它.也就是说,一个问题的解可由它的规模更小的子问题的解递推得出.由于子问题的交叠性质,所以采用递归地方法一次又一次地求解子问题时,进行了很多重复的工作.所以动态规划法建议:把子问题的解存入某个表中,通过表一步步反解出原始问题.斐波那契数列就是一个很好的例子: F(n) = F(n-1) + F(n-2)     当n≥2 F(0) = 0 F(1) = 1 如果直接采用递推公式求解第n个斐波那契数,那么会重复大量的无用工作,效率

动态规划_拦截导弹

被拦截的导弹应该依照飞来的高度组成一个非递增序列.求最长非递增序列的长度. #include <iostream> using namespace std; int main() { int h[2000], d[2000], c; //h表示 高度值, d表示最优值, c是能拦截的最多导弹数 int count = 0; //统计飞来的导弹数 while (cin >> h[count++] && h[count-1]); //输入高度 d[count-1] =

算法导论_动态规划_最长公共子序列

一.动态规划的概念 动态规划(Dynamic Programming)是通过组合子问题的解而解决整个问题的.分治是指将问题划分成一些独立的子问题,递归地求解各子问题,然后合并子问题的解而得到原始问题的解,与此不同,动态规划适用于子问题不是独立的情况,也就是各个子问题包含公共的子问题.在这种情况下,采用分治法会做许多不必要的工作,即重复地求解公共地子问题.动态规划算法对每个子问题只求解一次,将其结果保存在一张表中,从而避免每次遇到各个子问题时重新计算答案. 动态规划通常应用于最优化问题.此类问题可

动态规划_连续子数组的最大和

题目描述 HZ偶尔会拿些专业问题来忽悠那些非计算机专业的同学.今天测试组开完会后,他又发话了:在古老的一维模式识别中,常常需要计算连续子向量的最大和,当向量全为正数的时候,问题很好解决.但是,如果向量中包含负数,是否应该包含某个负数,并期望旁边的正数会弥补它呢?例如:{6,-3,-2,7,-15,1,2,2},连续子向量的最大和为8(从第0个开始,到第3个为止).给一个数组,返回它的最大连续子序列的和,你会不会被他忽悠住?(子向量的长度至少是1) 解答 就是在一个一维数组里找出一段,使其和最大.

动态规划_基础_任意子区间序列求和问题_滑动窗口解法_多种思路_分治思想演变

题目描述 给出一段序列,选出其中连续且非空的一段使得这段和最大. 输入描述 第一行是一个正整数 N ( 1 ≤ N ≤ 200000 ) ,表示了序列的长度. 接下来的 N 行包含 N 个绝对值不大于 10000 的整数 A [ i ] ,描述了这段序列. 输出描述 仅包括 1 个整数,为最大的子段和是多少,子段的最小长度为 1 . 样例输入 72-43-12-43 样例输出 4 Hint Origin: SidneyEdit by stdKonjac in 2020 解题思路: 关于求子区间求

动态规划_基础_最长公共子序列_多种方法_递归/dp

D: 魔法少女资格面试 题目描述 众所周知,魔法少女是一个低危高薪职业.随着近年来报考魔法少女的孩子们越来越多,魔法少女行业已经出现饱和现象!为了缓和魔法少女界的就业压力,魔法少女考核员丁丁妹决定增加魔法少女资质考核的难度.然而,即使如此,通过资质考核的魔法少女们数量仍然过多,因此,丁丁妹决心增加一轮面试,从而淘汰掉更多的预备魔法少女.具体而言,她打算对所有面试者询问这样一个问题:给两个长度为 n 的全排列,它们的最长公共子序列长度是多少?不幸的是,由于丁丁妹没有好好上过学,她自己也不知道答案是

算法导论_动态规划_最长回文子序列

一.问题的描述 回文序列(Palindromic sequence, Palindrome)是指正向遍历和反向遍历完全相同的序列,例如字符串"AAAAA"显然是一个回文序列,又如字符串"[email protected]"也是一个回文序列.现在,我们要在一个(字符)序列中找出最长回文子序列的长度.例如字符序列"BBABCBCAB",最长回文子序列是"BACBCAB"(可能不唯一),它的长度是7:子序列"BBBBB&q

动态规划_数字三角形

问题描述:在下面的数字三角形中寻找一条从顶部到底边的路径,使得路径上所经过的数字之和最大,路径上的每一步都只能往左下或右下走.只需要求出这个最大和即可,不必给出具体路径. 输入数据的要求:三角形的行数大于1小于等于100,数字为0--99. 输入格式: 5 //三角形的行数,下面是三角形 7 3 8 8 1 0 2 7 4 4 4 5 2 6 5 #include <iostream> using namespace std; const int N = 101; int a[N][N], n

动态规划_多重背包:Space Elevator

U - Space Elevator Time Limit:1000MS     Memory Limit:65536KB     64bit IO Format:%I64d & %I64u Submit Status Description The cows are going to space! They plan to achieve orbit by building a sort of space elevator: a giant tower of blocks. They have