首页 > 其他分享 >排列组合

排列组合

时间:2023-08-01 21:58:23浏览次数:27  
标签:return infact 组合 int 逆元 排列组合 mod

 排列:从 n个元素的集合 S 中,有序的选出 r 个元素,叫做 S  的一个 r 排列

排列数的性质:

第一条性质:(n*(n-1)*...*2*1)/((n-1-m+1)*...*2*1)=n!/(n-m)!;

第二条性质:m*(n-1)!/(n-m)!+(n-1)!/(n-1-m)!=(n-m+m)*(n-1)!/(n-m)!=n!/(n-m)!

 组合:

从 n 个元素的集合 S 中,无序的选出 r 个元素,叫做 S 的一个 r 组合。

组合数的性质:

 乘法递推组合数(时间复杂度o(n)):

 根据以上递推式,又因为边界c(n,0)=1,可以得出:

1     c[0] = 1;
2     for (register int i = 1; i * 2 <= n; i++) {
3         c[i] = (n - i + 1) * c[i - 1] / i;//必须先乘后除,不然可能会除不开
4         c[n - i] = c[i];//利用对称性质,减少时间复杂度
5     }

register 声明的变量是直接放在cpu的寄存器当中,而非就是通过内存寻址访问,这样就可以大大的提高程序的运行效率,还需要注意,register 声明变量只能在主函数或自定义内部。注意:是内部,定义在外面是会报错的。

 

以上仅限数较小时使用。

 

当数较大时,题目可能要求取模,需要用到逆元。

 1 const int N = 1e6 + 7, mod = 1e9 + 7;
 2 int n, m, k, t;
 3 int inv[N];//逆元
 4 int fact[N], infact[N];//阶乘结果,阶乘的逆元的结果
 5 
 6 void init(int n)
 7 {
 8     fact[0] = 1;//组合数c(n,0)=1;
 9     infact[0] = 1;//组合数为1的逆元为1
10     inv[1] = 1;//1的逆元为1;
11     for (int i = 2; i <= n; ++i)//先将1-n的所有逆元递推出来
12         inv[i] = 1ll * (mod - mod / i) * inv[mod % i] % mod;
13     for (int i = 1; i <= n; ++i) {
14         fact[i] = 1ll * fact[i - 1] * i % mod;
15         infact[i] = 1ll * infact[i - 1] * inv[i] % mod;
16         //每次除以一个数的mod就相当于乘这个数在该mod状态下的逆元
17     }
18 }
19 int C(int n, int m)//无序
20 {
21     if (n < m) return 0;
22     if (m == 0 || n == m) return 1;
23     return 1ll * fact[n] % mod * infact[m] % mod * infact[n - m] % mod;
24 }

也可以利用此方法求排列数:

1 int A(int n, int m)//有序
2 {
3     if (n < m || m < 0)return 0;
4     if (m == 0 || n == m)return 1;
5     return fact[n] % mod * infact[n - m] % mod;
6 }

对组合数取模还有一个叫卢卡斯定理。。。之后再学吧。。。整理一晚上排列组合了。

 再挂一个二项式定理:

 收工。。。。。。。。。。。

标签:return,infact,组合,int,逆元,排列组合,mod
From: https://www.cnblogs.com/DLSQS-lkjh/p/17599193.html

相关文章

  • 排列组合
    错排问题对于第n信,必然放在1~n-1号信封中。假设n号信放在1号信封中,考虑一号信放在哪放在n号信封中,还剩的n-2封信和信封构成了n-2的子问题f(n-2)放在k号信封(\(2\lek<n\))f(n-1)因为n可以放在n-1个位置。所以(f(n-1)+f(n-2))*(n-1)P1595信封问题板子题,不多说了P4071[SDO......
  • 【算法】在各种排列组合下,计算零钱找零方式数量
    写一个函数,在给定一系列硬币面额的情况下,计算你可以用多少种不同的方式来兑换一笔钱。例如,如果你有面额为1和2的硬币,有3种方法可以为4找零:1+1+1+1,1+1+2,2+2。硬币的顺序无关紧要:1+1+2==2+1+1此外,假设你有无限数量的硬币。示例调用,一个金额和一系列独特面额的硬币:CountCombin......
  • 算法——排列组合
    排列、组合适合回溯法,保存当前状态什么时候使用used数组,什么时候使用begin变量有些朋友可能会疑惑什么时候使用used数组,什么时候使用begin变量。这里为大家简单总结一下:排列问题,讲究顺序(即[2,2,3]与[2,3,2]视为不同列表时),需要记录哪些数字已经使用过,此时用**u......
  • 排列组合
    排列组合目录排列组合排列数线排列圆排列:可重排列(其中一种)重集全排列:错位排列:组合数无重组合可重组合不相邻组合二项式定理恒等式(简化复杂度)常用:前言:第一次尝试边上课边记录笔记…可能思路会有一点小乱,排列数线排列公式:p(n,m)=!n/!(n-m)推论1:p(n,m)=n*p(n-1,m-1)推论2:p(......
  • 基础排列组合学习笔记
    排列组合是数学中一项非常重要、基础的内容,可以解决许多与计数有关的问题。让我们先从最基本的数数学起。前置知识加法原理假设你现在有\(a_0\)个物品,所有物品互不相同。你要从中拿一个物品出来,拿出的物品可能有几种?显然是\(a_0\)种,因为每一个物品互不相同,每一个物品都可......
  • js 实现排列组合
    组合:(不考虑顺序,无重复)//测试用例letdataArr=[1,2,3,4,5];functioncombination(dataArr,remainNum,currentArr){if(remainNum===0){console.log(...currentArr);return;}for(leti=0;i<dataArr.length+1-remainNum;i++){......
  • 排列组合的实现Cmn,Amn
    递归方法:publicclassCombination{/***计算从m个元素中选n个元素的组合数Cmn*@paramm总共有m个元素*@paramn从中选n个元素*@return组合数Cmn的值*/publicstaticintCmn(intm,intn){if(n==0||n==m){......
  • 排列组合的应用
    目录应用应用1:Leetcode.39题目分析代码实现方法一方法二应用2:Leetcode.40题目分析代码实现应用3:Leetcode.216题目分析代码实现方法一方法二应用4:Leetcode.78题目分析代码实现应用5:Leetcode.90题目分析代码实现应用6:Leetcode.77题目分析代码实现应用7:Leetcode.46题目分析代码实现应......
  • 番外篇:分享一道用Python基础+蒙特卡洛算法实现排列组合的题目(附源码)
    今日鸡汤夕阳无限好,只是近黄昏。    大家好,我是Python进阶者。    是不是觉得很诧异?明明上周刚发布了这篇:分享一道用Python基础+蒙特卡洛算法实现排列组合的题目(附源码),今天又来一篇,名曰番外篇!其实今天是想给大家分享【......
  • 分享一道用Python基础+蒙特卡洛算法实现排列组合的题目(附源码)
    今日鸡汤沙场烽火连胡月,海畔云山拥蓟城。    大家好,我是Python进阶者。这篇文章的题目真的是很难取,索性先取这个了,装个13好了。前言    前几天在才哥交流群里,有个叫【RickXiang】的粉丝在Python交流群里问了一道关于排列组合的问题,初步一看觉得很简单,实际上确实是有难度的......