#include <fstream>
#include <algorithm>
using namespace std;
#define f first
#define s second
ifstream fin("scmax.in");
ofstream fout("scmax.out");
int i,j,n,m,v[100010],sol[100010],ans,ld,st,k;
pair< int , pair< int , int > >arb[4*100010];
pair<int,int> norm[100010];
void query( int nod, int left, int right, int pozMax, int lim )
{
int middle = ( left + right ) / 2;
if( left > lim ) return; ///DACA AM IESIT CU INTERVALUL IN DREAPTA LIMITEI
if( arb[ nod ].f < ans ) return; ///NU MA INTERESEAZA ACEST INTERVAL
if( right < lim ) ///SUNT IN INTERIOR
{
if( arb[ nod ].s.f > pozMax )
return;
if( arb[ nod ].s.s < pozMax && v[ arb[ nod ].s.s ] < v[ norm[ i ].s ] )
{
if( arb[ nod ].f > ans )
{
ans = arb[ nod ].f;
if( ans > k )
{
k = ans;
st = norm[ i ].s;
}
sol[ pozMax ] = arb[ nod ].s.s;
return;
}
}
if( left == right )
return;
if( arb[ 2 * nod ].s.f < pozMax )///INTERVALUL DIN STANGA REPREZINTA UN PUNCT DE INTERES
query( 2 * nod , left , middle , pozMax , lim );
if( arb[ 2 * nod + 1 ].s.f < pozMax )///INTERVALUL DIN DREAPTA REPREZINTA UN INTERVAL DE INTERES
query( 2 * nod + 1 , middle + 1 , right , pozMax , lim );
return;
}
if( left == right )
return;
query( 2 * nod , left , middle , pozMax , lim);
if( middle + 1 < lim )
query( 2 * nod + 1 , middle + 1 , right , pozMax , lim );
}
void update( int nod, int left, int right, int src, int up )
{
if( left == right && left == src )
{
arb[ nod ] = make_pair( up , make_pair( norm[ i ].s , norm[ i ].s ) );
if( up == k )
st = left;
return;
}
if( left <= src && src <= right )
{
int middle = ( left + right ) / 2;
if( src <= middle )
update( 2 * nod , left , middle , src , up );
else
update( 2 * nod + 1 , middle + 1 , right , src , up );
if( arb[ 2 * nod ].f > arb[ 2 * nod + 1 ].f )
arb[ nod ] = arb[ 2 * nod ];
else
arb[ nod ] = arb[ 2 * nod + 1 ];
arb[ nod ].s.f = min( arb[ 2 * nod ].s.f , arb[ 2 * nod + 1 ].s.f );
}
}
void afis( int k )
{
if( k == 0 )
return;
afis( sol[ k ] );
fout<<v[ k ]<<' ';
}
int main()
{
fin>>n;
for( i = 1 ; i <= n ; i++ )
{
fin>>v[ i ];
norm[ i ] = make_pair( v[ i ] , i );
}
sort( norm + 1 , norm + n + 1 );
for( i = 1 ; i <= n ; i++ )
{
ld = norm[ i ].s;
ans = 0;
query( 1 , 1 , n , ld , i );
update( 1 , 1 , n , i , ans + 1 );
}
fout<<arb[1].f<<'\n';
afis( st );
return 0;
}