POJ1833 - 排列 - 全排列模板题 - C++ STL 全排列函数详解
全排列概念
从n个不同元素中任取m(m≤n)个元素,按照一定的顺序排列起来,叫做从n个不同元素中取出m个元素的一个排列。当m=n时所有的排列情况叫全排列。如果这组数有n个,那么全排列数为n!个。比如a,b,c的全排列一共有3!= 6 种 分别是{a, b, c}、{a, c, b}、{b, a, c}、{b, c, a}、{c, a, b}、{c, b, a}。
全排列求上下k个排列组合
这里先说两个概念:“下一个排列组合”和“上一个排列组合”,对序列 {a, b, c},每一个元素都比后面的小,按照字典序列,固定a之后,a比bc都小,c比b大,它的下一个序列即为{a, c, b},而{a, c, b}的上一个序列即为{a, b, c},同理可以推出所有的六个序列为:{a, b, c}、{a, c, b}、{b, a, c}、{b, c, a}、{c, a, b}、{c, b, a},其中{a, b, c}没有上一个元素,{c, b, a}没有下一个元素。
-
全排列函数:
next_permutation
:求下k个排列组合 -
函数模板:
next_permutation(arr, arr+size)
-
函数功能: 返回值为bool类型,当当前序列不存在下一个排列时,函数返回false,否则返回true,排列好的数在数组中存储
-
注意:在使用前需要对欲排列数组按升序排序,否则只能找出该序列之后的全排列数。比如,如果数组num初始化为2,3,1,那么输出就变为了:{2 3 1}
1. `prev_permutation`:求上k个排列组合
2. 函数模板:`prev_permutation(arr, arr+size)`
3. 函数功能: 同上
4. 注意:在使用前需要对欲排列数组按==降序排序==,否则只能找出该序列之后的全排列数。
##题意
对于每组输入数据,输出一行,n个数,中间用空格隔开,表示输入排列的下k个排列。
##思路
==全排列模板题==,但是因为是直接输出当前排列的下k个排列,而不是全部情况,所以需要注意的就是==本题不需要排序==!!!
##AC代码
==在C++上提交AC,G++TLE==
```
#include<stdio.h>
#include<string.h>
#include<algorithm>
using namespace std;
int a[1050];
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
int n,k;
scanf("%d %d",&n,&k);
for(int i=0; i<n; i++)
scanf("%d",&a[i]);
// sort(a,a+n);
// for(int i=1;i<=k;i++)
while(k--)
next_permutation (a,a+n);
for(int i=0; i<n-1; i++)
printf("%d ",a[i]);
printf("%d\n",a[n-1]);
}
return 0;
}
```
##生成1~n的全排列
```
#include <stdio.h>
#include <algorithm>
using namespace std;
int main()
{
int n;
while(~scanf("%d",&n)&&n){
int a[100];
for(int i=0;i<n;i++)
scanf("%d",&a[i]);
sort(a,a+n);
do
{
for(int i=0;i<n;i++)
printf("%d ",a[i]);
printf("\n");
}while(next_permutation(a,a+n));
}
return 0;
}
```