Cod sursa(job #1539051)

Utilizator DysKodeTurturica Razvan DysKode Data 30 noiembrie 2015 09:52:05
Problema Subsir crescator maximal Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 2.66 kb
#include <fstream>
#include <algorithm>
using namespace std;

ifstream fin("scmax.in");
ofstream fout("scmax.out");

int Vec[100010],i,j,Constr[100010],Arb[4 * 100010],st,n,maxl,l,p;
pair<int,int>SrtVec[100010];

void GetLength( int nod, int left, int right, int lim, int &poz, int &ln )
{
    int middle = ( left + right ) / 2;

    if( right <= lim )
    {
        if( Arb[ nod ] > ln )
        {
            while( left != right )
            {
                if( Arb[ 2 * nod ] == Arb[ nod ] )///LEFT SON
                {
                    right = middle;
                    middle = ( left + right ) / 2;
                    nod = 2 * nod;
                }
                else///RIGHT SON
                {
                    left = middle + 1;
                    middle = ( left + right ) / 2;
                    nod = 2 * nod + 1;
                }
            }
            poz = left;
            ln = Arb[ nod ];
        }
        return;
    }

    GetLength( 2 * nod , left , middle , lim , poz , ln );
    if( middle + 1 <= lim )
        GetLength( 2 * nod + 1 , middle + 1 , right , lim , poz , ln );
}

void Update( int nod, int left, int right , int poz, int val )
{
    if( left == right )
    {
        Arb[ nod ] = val;
        return;
    }

    int middle = ( left + right ) / 2;

    if( poz <= middle )
        Update( 2 * nod , left , middle , poz , val );
    else
        Update( 2 * nod + 1 , middle + 1 , right , poz , val );

    Arb[ nod ] = max( Arb[ 2 * nod ] , Arb[ 2 * nod + 1 ] );
}

void GetVec( int k , int l )
{
    if( k == 0 )
        return;
    GetVec( Constr[ k ] , l - 1 );
    Arb[ l ] = Vec[ k ];
}

bool cmp( pair<int,int>a,pair<int,int>b )
{
    if( a.first < b.first )
        return true;
    else if( a.first > b.first )
        return false;
    else
        return a.second>b.second;
}

int main()
{
    fin>>n;
    for( i = 1; i <= n ; i++ )
    {
        fin>>Vec[ i ];
        SrtVec[ i ].first = Vec[ i ];
        SrtVec[ i ].second = i;
    }

    sort( SrtVec + 1 , SrtVec + n + 1 , cmp );

    for( i = 1 ; i <= n ; i++ )
    {
        p = 0;
        l = 0;
        GetLength( 1 , 1 , n , SrtVec[ i ].second , p , l );
        if( l == 0 )
        {
            p = 0;
        }
        if( l >= maxl )
        {
            maxl = l;
            st = SrtVec[ i ].second;
        }
        Constr[ SrtVec[ i ].second ] = p;
        Update( 1 , 1 , n , SrtVec[ i ].second , l + 1 );
    }

    GetVec( st , maxl + 1 );

    fout<<maxl+1<<'\n';
    for( i = 1 ; i <= maxl + 1 ; i++ )
    {
        fout<<Arb[ i ]<<' ';
    }

return 0;
}