Pagini recente » Monitorul de evaluare | Cod sursa (job #3338593) | Monitorul de evaluare | Cod sursa (job #3342286) | Cod sursa (job #3309780)
#include <bits/stdc++.h>
#define NMAX 100001
using namespace std;
ifstream in("scmax.in");
ofstream out("scmax.out");
int a[NMAX];
int sortat[NMAX], ult_poz[NMAX], lungime[NMAX];
pair<int, int> aib[NMAX]; /// aib[i].first = maximul iar aib[i].second = pozitia elementului maxim
int cautare_binara(int val, int n) ///cautam cate numere din sir sunt mai mici ca val
{
int st=0, dr=n, poz=0;
while(st<=dr)
{
int mij=st+(dr-st)/2;
if(sortat[mij]<=val)
{
poz=mij;
st=mij+1;
}
else
{
dr=mij-1;
}
}
return poz;
}
void actualizare(int val, int i, int poz, int n) ///actualizare aib
{
while(poz<=n)
{
if(val>aib[poz].first)
{
aib[poz].first=val;
aib[poz].second=i;
}
poz+=(poz&(-poz));
}
}
pair<int, int> maxim(int poz, int n) ///maximul pe intervalul [1, poz] si pozitia sa
{
pair<int, int> maxim={0, 0};
while(poz>0)
{
if(aib[poz].first>maxim.first)
{
maxim=aib[poz];
}
poz-=(poz&(-poz));
}
return maxim;
}
int main()
{
int n;
in >> n;
for(int i=1; i<=n; i++)
{
in >> a[i];
sortat[i]=a[i];
}
sort(sortat+1, sortat+n+1);
int l_max=0, poz_lmax=0; ///lungimea maxima si pozitia din vectorul a a ultimului element adaugat
for(int i=1; i<=n; i++)
{
int poz=cautare_binara(a[i], n);
pair<int, int> l_maxim=maxim(poz-1, n); ///lungimea maxima si pozitia ultimului element al subsirului crescator de lungime maxima de pana acum (care are ultimul element mai mic ca a[i])
lungime[i] = l_maxim.first + 1;
ult_poz[i] = l_maxim.second;
if(lungime[i]>l_max)
{
l_max=lungime[i];
poz_lmax=i;
}
actualizare(lungime[i], i, poz, n);
}
out << l_max << "\n";
vector<int> lis; ///subsirul cerut
while(poz_lmax!=0)
{
lis.push_back(poz_lmax);
poz_lmax=ult_poz[poz_lmax];
}
reverse(lis.begin(), lis.end());
for(auto& i : lis) ///afisam subsirul
out << a[i] << " "; out << "\n";
return 0;
}