LongestIncreasingSubsequence.cpp 1020 B

12345678910111213141516171819202122232425262728293031323334
  1. // Given a list of numbers of length n, this routine extracts a
  2. // longest increasing subsequence.
  3. //
  4. // Running time: O(n log n)
  5. //
  6. // INPUT: a vector of integers
  7. // OUTPUT: a vector containing the longest increasing subsequence
  8. // #define STRICTLY_INCREASNG // buggué, quand on retrouve la suite ?
  9. VI LongestIncreasingSubsequence(VI v) {
  10. VPII best;
  11. VI dad(v.size(), -1);
  12. for (int i = 0; i < v.size(); i++) {
  13. #ifdef STRICTLY_INCREASNG
  14. PII item = make_pair(v[i], 0);
  15. VPII::iterator it = lower_bound(best.begin(), best.end(), item);
  16. item.second = i;
  17. #else
  18. PII item = make_pair(v[i], i);
  19. VPII::iterator it = upper_bound(best.begin(), best.end(), item);
  20. #endif
  21. if (it == best.end()) {
  22. dad[i] = (best.size() == 0 ? -1 : best.back().second);
  23. best.push_back(item);
  24. } else {
  25. dad[i] = dad[it->second];
  26. *it = item;
  27. }
  28. }
  29. VI ret;
  30. for (int i = best.back().second; i >= 0; i = dad[i])
  31. ret.push_back(v[i]);
  32. reverse(ret.begin(), ret.end());
  33. return ret;
  34. }