详解STL中next_permutation()函数实现

来源:互联网 发布:渡边麻友ins事件 知乎 编辑:程序博客网 时间:2024/06/14 12:27

前几天,遇到一个可以用穷举法解决的问题,就是中给定几个数子,让凑出等式的类型。之前,我都是用写个函数递归调用,今天突然想到其实有一个更简单的方式来实现穷举,那就是使用STL中的next_permutation()库函数(注:头文件中包含进#include<algorithm>即可)。我最近在学Java,但是在Java中貌似没有这种方法,所以我想到了自己来实现这个方法。

首先再来详细介绍一下next_permutation()

完整形式:

bool next_permutation(T<?> a, int first, int last)

输入:第一个参数是一个数组,第二个参数是起始下标,第三个参数是终止下标

返回值:如果有下一个排列,就返回true,没有就返回false

函数作用:如果一个数组中的元素有下一个全排列,就将它改为下一个全排列,并返回true,否则返回false


我们将该问题抽象并整理之后,明确如下:

问题描述:给定一个n个字母组成的字符串s1{a1,a2,a3,……,an},我们要求的就是:重新排列着n个字母,组成另一个字符串s2,它的字典序仅大于字符串s1。

分析:首先,我们用递归的思想来分析该问题。

降低问题规模:①仅比{a2, a3, ……,an}的字典序大的字符串存在,为ss,那么我们问题的解就是{a1, ss}。②仅比{a2, a3, ……,an}的字典序大的字符串不存在,那么{a2,a3,……,an}是字典序最大的了,也就是{a2,a3,……,an}按从大到小的顺序排列。我们就从后往前找到第一个大于a1的字母ai,将a1与ai互换,就可以得到我们想要的字符串了。

③仅比{a2, a3, ……,an}的字典序大的字符串不存在,且{a2, a3, ……,an}中找不到比a1大的字母,则{a1,a2,a3,……,an}已经是字典序最大的字符串了。

按照上面的分析,我们可以很容易写出递归实现的代码。


那么,我们如何用递推的形式来完成这个功能呢?

我们从字符序列的最尾端开始,向前找。

1、比较最后两个字符a(n-1),a(n),如果字符a(n-1) <a(n-1),这a(n-1)与a(n)互换即可,否则执行第2步

2、a(n-2)是不是比a(n-1)和a(n)都要大,如果不是,这找到a(n-2)的插入位置,互换,否则执行第3步

3、a(n-3)是不是比a(n-2)、a(n-1)、a(n)都要大,不知找到a(n-3)的插入位置,互换,否则执行第4步

.

.

.

.

至此我们可以用while循环来递推实现该功能了。。。。


0 0