如何解决N的迭代算法选择K,无重复,顺序重要
我正在寻找一种迭代算法,以获取从一组N个元素中提取的K个元素的所有排列,而无需重复(即,不进行替换),并且其顺序很重要。 我知道排列的数量必须为N!/(N-K)!。 你有什么想法吗? 谢谢。
伊万
解决方法
方法1:
简单的想法:
由于顺序很重要,因此我们将尝试使用next_permutation
algorithm。 next_permutation
函数可提供下一个字典上唯一的排列。
算法:
- 创建一个新数组A,其大小等于原始数组的大小。
- 分配最后k个数字1,2,3,.. k,以使k结尾。将其余数字分配为0。
- 现在,当使用
next_permutation
遍历排列时,仅选择原始数组中的索引,其中A的值大于0,保持顺序。
正确性说明:
由于在新创建的数组中有N个数字,其中N-k个重复,因此唯一的总排列变为N!/(N-k)!这给了我们想要的结果。
示例:
输入:X = [1,3],k = 2
现在,我们创建A = [0,1,2]。
所有排列:
[0,2],[0,1],[1,0],[2,0].
仅从原始数组中选择这些排列的索引 i ,其中A [i]> 0,将产生
[2,3],[3,1].
如果要按排序的顺序在上方使用,请使用负数,并使用-k,-k-1,..- 1初始化前k个数字,然后使用0初始化剩余的k个数字,并稍加修改即可应用该算法,方法是在原始数组中选择索引 i ,以便A [i]
旁注:
如果顺序无关紧要,请使用A
-1s初始化k
,并在0之前保持-1s,然后使用迭代置换算法,该算法将从N个项目中产生唯一的k个选择。
方法2 :(优于方法1)
算法:
- 首先选择前K个数字,然后填充到数组
A
中,它将存储原始数组中所选元素的索引。我们将其标记为首选。 - 现在按字典顺序获得所有剩余的排列。
- 如何获得考虑订单的下一个组合?如果可能,我们将对选择进行置换,否则按字典顺序返回更大的选择。
如果排列已用尽,则按字典顺序获得下一个选择的想法:
考虑当前的组合,找到最右边的元素 尚未达到可能的最高价值。一旦找到这个 元素,我们将其加1,然后将最低有效值分配给 所有后续元素。
来自:https://cp-algorithms.com/combinatorics/generating_combinations.html
示例:
输入:X = [1,3,4],k = 3
现在,我们创建A = [0,2] // initialization [0,1] // next permutation ... // all permutations of [0,2] ... [2,0] // reached last permutation of current selection [0,3] // get next selection in lexicographic order as permutations are exhausted ... [3,0] // reached last permutation of current selection [0,0] // reached last permutation of current selection [1,1] // reached last permutation of current selection
代码(基于0的索引,因此从0-k-1初始化开始):
bool next_combination_with_order(vector<int>& a,int n,bool order_matters=true) {
int k = (int)a.size();
if(order_matters && std::next_permutation(a.begin(),a.end()))return True; // check if next permutation exists otherwise move forward and get next unique combination
// if `a` was already in descending order,// next_permutation returned false and changed the array to sorted order.
// now find next combination if possible
for (int i = k - 1; i >= 0; i--) {
if (a[i] < n - k + i + 1) {
a[i]++;
for (int j = i + 1; j < k; j++)
a[j] = a[j - 1] + 1;
return true;
}
}
return false;
}
参考:
下一个排列:
https://en.wikipedia.org/wiki/Permutation#Generation_in_lexicographic_order
std::next_permutation Implementation Explanation
下一个无顺序组合:
https://cp-algorithms.com/combinatorics/generating_combinations.html
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。