BOJ 23245 - Similarity

image.png

헷갈렸지만 결국 pair로 된 길이 3의 LIS를 세는 문제였다.

$x[i]=(p_i,\,q_i)$ 라고 할 때, $x[i]<x[j]$ 인 조건은

$$ p_i < p_j~ \& ~q_i < q_j $$

이 조건을 처리해주기에 유의할 점은 $p_i$ 로 정렬을 한다음에 같은 $p_i$ 가 이전에 업데이트한 값들에 영향을 받지 않도록 잘 처리해주어야 한다는 것이다.

같은 $p_i$ 를 같는 인덱스들을 모두 묶어서 먼저 쿼리를 모두 날린다음에 그 다음 업데이트를 한 번에 해주고 다음 $p$ 로 넘어간다.

struct fenwick {  
   ...
};  
  
void solve() {  
   int n;  
   cin >> n;  
   vector<pi> p(n);  
   vi a(n), b(n);  
   fv(a);  
   fv(b);  
   for (int i = 0; i < n; i++) p[i].fi = a[i];  
   for (int i = 0; i < n; i++) p[i].se = b[i];  
  
   vi v;  
   for (int i: a) v.pb(i);  
   for (int i: b) v.pb(i);  
   uniq(v);  
   for (auto&[a, b]: p) a = lbi(v, a), b = lbi(v, b);  
   int V = sz(v);  
  
   fenwick fenw1(V), fenw2(V);  
   sort(all(p));  
  
   int ans = 0;  
   for (int i = 0; i < n; i++) {  
      int j = i;  
      while (j < n && p[i].fi == p[j].fi)j++;  
      j--;  
  
      vi ret1_pending;  
      for (int k = i; k <= j; k++) {  
         int ret = fenw1.q(0, p[k].se - 1);  
         ret1_pending.pb(ret);  
         ans += fenw2.q(0, p[k].se - 1);  
      }  
  
      for (int k = i; k <= j; k++) {  
         fenw1.upd(p[k].se, 1);  
         fenw2.upd(p[k].se, ret1_pending[k - i]);  
      }  
      i = j;  
   }  
   cout << ans;  
}

Tags:

Categories:

Updated:

Comments