Cod sursa(job #329861)

Utilizator ssergiussSergiu-Ioan Ungur ssergiuss Data 7 iulie 2009 20:40:29
Problema Subsir crescator maximal Scor 10
Compilator cpp Status done
Runda Arhiva educationala Marime 1.78 kb
# include <algorithm>
using namespace std;

# define DIM 1 << 17

struct sir {

    int poz, val;
};

int n, max0, poz0, a[ DIM ], aib[ DIM ], ant[ DIM ], bst[ DIM ];
sir s[ DIM ];

inline int lsb ( int x ) {

    return x & ( x - 1 ) ^ x;
}

int cmp ( sir x, sir y ) {

    if ( a[ x.poz ] > a[ y.poz ] )
        return 0;

    return 1;
}

int query ( int poz ) {

    int aux;

    for ( aux = 0; poz; poz -= lsb ( poz ) )
        if ( bst[ aib[ poz ] ] > bst[ aux ] )
            aux = aib[ poz ];

    return aux;
}

void upd ( int poz, int val ) {

    for ( ; poz <= n; poz += lsb( poz ) )
        if ( bst[ val ] > bst[ aib[ poz ] ] )
            aib[ poz ] = val;
}

void norm () {

    int i, cnt;

    sort ( s + 1, s + n + 1, cmp );
    cnt = 1;
    for ( i = 1; i <= n; ++ i ) {

        s[ i ].val = cnt;
        for ( ; i < n && a[ s[ i + 1 ].poz ] == a[ s[ i ].poz ]; ++ i )
            s[ i + 1 ].val = cnt;
        ++ cnt;
    }
}

void print ( int poz ) {

    if ( ant[ poz ] )
        print ( ant[ poz ] );
    printf ( "%d ", a[ s[ poz ].poz ] );
}

void read () {

    int i;

    scanf ( "%d", &n );
    for ( i = 1; i <= n; ++ i ) {

        scanf ( "%d", &a[ i ] );
        s[ i ].poz = i;
    }
}

void solve () {

    int i;

    norm ();
    for ( i = 1; i <= n; ++ i ) {

        ant[ i ] = query ( s[ i ].val - 1 );
        bst[ i ] = bst[ ant[ i ] ] + 1;
        upd ( i, s[ i ].val );
        if ( bst[ i ] > max0 ) {

            max0 = bst[ i ];
            poz0 = i;
        }
    }
    printf ( "%d\n", max0 );
    print ( poz0 );
}

int main () {

    freopen ( "scmax.in", "r", stdin );
    freopen ( "scmax.out", "w", stdout );

    read ();
    solve ();

    return 0;
}