Cod sursa(job #1108305)

Utilizator andrei.sfrentSfrent Andrei andrei.sfrent Data 15 februarie 2014 16:08:56
Problema Subsir crescator maximal Scor 0
Compilator cpp Status done
Runda Arhiva educationala Marime 1.36 kb
#include <cstdio>

using namespace std;

// #define MY_DEBUG

int N, L;
int v[100001], M[100001], P[100001], S[100001];

void read() {
  scanf("%d", &N);
  for(int i = 1; i <= N; ++i) {
    scanf("%d", v + i);
  }
}

inline int max(int x, int y) { return x > y ? x : y; }

void write_vector(int *v, int li, int ls) {
  for(int i = li; i <= ls; ++i) {
    printf("%4d ", v[i]);
  }
  printf("\n");
}

int search(int li, int ls, int i) {
  if(li > ls) return ls;
  else {
    int mid = li + (ls - li) / 2;
    if(v[M[mid]] > v[i]) {
      return search(li, mid - 1, i);
    } else {
      return search(mid + 1, ls, i);
    }
  }
}

void scmax() {
  L = 0;
  for(int i = 1; i <= N; ++i) {
    int j = search(1, L, i);
    P[i] = M[j];
    if(j == L || v[i] < v[M[j + 1]]) {
      M[j + 1] = i;
      L = max(L, j + 1);
    }
#ifdef MY_DEBUG
    printf("L: %d\n", L);
    printf("v: ");
    write_vector(v, 1, i);
    printf("P: ");
    write_vector(P, 1, i);
    printf("M: ");
    write_vector(M, 1, L);
    printf("\n");
#endif
  }
}

void write() {
  S[0] = v[M[L]];
  int u = M[L];
  for(int i = 1; i < L; ++i) {
    S[i] = v[P[u]];
    u = P[u];
  }
  for(int i = L - 1; i >= 0; --i) {
    printf("%d ", S[i]);
  }
  printf("\n");
}

int main(int argc, char *argv[]) {
  freopen("scmax.in", "r", stdin);
  freopen("scmax.out", "w", stdout);

  read();
  scmax();
  write();

  return 0;
}