permutation

在标准库算法中,prev_permutation和next_permutation应用在数列操作上比较广泛.

这个函数可以计算一组数据的全排列.包含在algorithm头文件中.

调用next_permutation使数列逐次增大,这个过程按照字典序增,同理prev_permutation按字典序递减.

如数组a[3]= {0, 1, 2} 有6种排序

0 1 2

0 2 1

1 0 2

1 2 0

2 0 1

2 1 0

令初始排列为 0 1 2 

next_permutation(a, a+ 3);

->0 2 1

prev_permutation(a, a+ 3);

->0 1 2

现在用操作符重载来实现:

#include<iostream>
#include<algorithm>
using namespace std;
class permu {
    public:
        permu(int n = 1, int state = 0) : n(n), state(state) {
            maxn = 1;
            for (int i = 0; i < n; i++) {
                a[i] = i;
                maxn *= i+1;
            }
            int tmp = state;
            while (tmp--) {
                ++(*this);
            }
        }
        permu & operator ++() {
            state++;
            if (state == maxn) {
                state = 0;
                for (int i = 0; i < n; i++) a[i] = i;
                return *this;
            }
            next_permutation(a, a+n);
            return *this;
        }
        permu operator ++(int x) {
            permu tmp(*this);
            ++(*this);
            return tmp;
        }
        permu & operator --() {
            state--;
            if (state == -1) {
                state = maxn-1;
                for (int i = 0; i < n; i++) a[i] = n-i-1;
                return *this;
            }
            prev_permutation(a, a+n);
            return *this;
        }
        permu operator --(int x) {
            permu tmp(*this);
            --(*this);
            return tmp;
        }
        friend ostream& operator << (ostream& os, const permu& x) {
            os << x.a[0];
            for (int i = 1; i < x.n; i++) os << " " << x.a[i];
            return os;
        }
    private:
        int n;
        int a[11];
        int state;
        int maxn;
};

main函数:

#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
using namespace std;
int main() {
    int n, m;
    cin >> n >> m;
    permu a(n);  // n是排列的长度。初始排列为0,1,2,...,n-1
    permu b = a;
    b = ++a;
    cout << b << endl;
    b = a++;
    cout << b << endl;
    for (int i = 0; i < m; i++) {
        --a;
    }
    b = a--;
    cout << a << endl;
    cout << b << endl;
}




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值