
#include "comb/perm-rev.h"

#include "comb/comb-print.h"
#include "comb/mixedradix.h"
#include "perm/perminvert.h"

//#include "comb/fact2perm.h"
//#include "aux1/copy.h"

#include "aux0/factorial.h"
#include "comb/check-permgen.h"
#include "jjassert.h"

#include "fxtio.h"
#include "demo/nextarg.h"
#include "fxttypes.h"

//#include "perm/perminvert.h"


//% Permutations by prefix reversions, CAT algorithm.

//#define TIMING // uncomment to disable printing



int
main(int argc, char **argv)
{
    ulong n = 4;
    NXARG(n, "Number of elements to permute");
    bool dfz= true; // whether to print dots for zeros

    perm_rev P(n);
    P.first();
//    P.last();

    ulong ct = 0;
    const ulong *x = P.data();
    ulong *t1 = new ulong[n];  // aux
//    ulong *t2 = new ulong[n];  // aux

    check_permgen C(n);
    C.first(t1);  // inverse permutations(!)
    const ulong nfh = factorial(n)/2;

    do
    {
#ifndef TIMING
        cout << setw(4) << ct << ":";
        P.print("    ", dfz);
        print_mixedradix("    ", P.d_, n-1, dfz);

        make_inverse(x, t1, n);
        print_perm("        ", t1, n, dfz);

        if ( ct<nfh )
        {
            jjassert( ! C.is_repeat() );
            jjassert( ! C.is_repeat_rev() );
        }

//        copy(x, t1, n);
//        reverse(t1, n);
//        perm2ffact_rev(t1, n, t2);
//        print_mixedradix("    ", t2, n-1, dfz);

        cout << endl;
#endif
        ++ct;
    }
    while ( P.next() );
//    while ( P.prev() );


    cout << endl;
    cout << " ct=" << ct << endl;
    cout << endl;

    delete [] t1;
//    delete [] t2;

    return 0;
}
// -------------------------

/*
Timing:
 time ./bin 12
 ct=479001600
./bin 12  4.23s user 0.02s system 99% cpu 4.249 total
 ==> 479001600/4.23 ==  113,239,148 permutations per second

*/

/// Emacs:
/// Local Variables:
/// MyRelDir: "demo/comb"
/// makefile-dir: "../../"
/// make-target: "1demo DSRC=demo/comb/perm-rev-demo.cc"
/// make-target2: "1demo DSRC=demo/comb/perm-rev-demo.cc DEMOFLAGS=-DTIMING"
/// End:

