제출 #1255777

#제출 시각아이디문제언어결과실행 시간메모리
1255777madamadam33개의 봉우리 (IOI25_triples)C++20
23.08 / 100
2095 ms1864 KiB
#include "triples.h"
#include <bits/stdc++.h>

using namespace std;

typedef long long ll;
using vi = vector<int>;
using vvi = vector<vi>;
using vl = vector<ll>;
using vvl = vector<vl>;
using pi = pair<int, int>;

#define FOR(i, a, b) for (int i = a; i < b; i++)
#define ROF(i, a, b) for (int i = a; i >= b; i--)
#define each(a, x) for (auto &a : x)
#define all(x) (x).begin(), (x).end()
#define bg(x) (x).begin()
#define en(x) (x).end()
#define rev(x) reverse(all(x))
#define sz(x) int((x).size())
#define srt(x) sort(all(x))
#define cnt(a, x) count(all(x), a)
#define trace(x) each(a, (x)) cout << a << " "
#define mp make_pair
#define pb push_back
#define lb lower_bound
#define ub upper_bound

struct DSU {
  int n; vi par, siz;

  DSU() {};
  DSU(int N) {
    n = N; par.resize(n); siz.assign(n, 1);
    iota(all(par), 0);
  }

  int find(int v) {
    if (par[v] == v) return v;
    return par[v] = find(par[v]);
  }

  void unite(int a, int b) {
    a = find(a); b = find(b);
    if (a != b) {
      if (siz[a] < siz[b]) swap(a, b);
      par[b] = a;
      siz[a] += siz[b];
    }
  }
};

ll brute(vi h) {
  int n = sz(h);
  ll ans = 0;

  // cerr << "brute function: \n";
  FOR(i, 0, n) {
    FOR(j, i+1, n) {
      FOR(k, j+1, n) {
        // vi d = {k - j, k - i, j - i}, f = {h[i], h[j], h[k]};
        // srt(d); srt(f);
        int d1 = min({k-j, k-i,j-i}), d3 = max({k-j, j-i, k-i});
        int d2 = (k-j) ^ (k-i) ^ (j-i) ^ d1 ^ d3;
        int f1 = min({h[i], h[j], h[k]}), f3 = max({h[i], h[j], h[k]}); 
        int f2 = h[i] ^ h[j] ^ h[k] ^ f1 ^ f3;
        // bool valid = d[0] == f[0] && d[1] == f[1] && d[2] == f[2];
        // if (!valid) continue;
        // ans++;
        // cerr << i << " " << j << " " << k << "\n";
        if (d1 == f1 && d2 == f2 && d3 == f3) ans++;
      }
    }
  }

  return ans;
}

struct Triple {
  int i, j, k;

  Triple() {};
  Triple(int I, int J, int K) {
    i = min({I, J, K});
    k = max({I, J, K});
    j = (I ^ J ^ K) ^ i ^ k; // lol
  }

  const bool operator<(const Triple &other) const {
    if (i != other.i) return i < other.i;
    if (j != other.j) return j < other.j;
    
    return k < other.k;
  }
};

ll increasing(vi h) {
  int n = sz(h);
  
  set<Triple> used;
  FOR(i, 0, n) {
    int k = i - h[i];
    if (k < 0) continue;

    int j1 = k + h[k], j2 = i - h[k];
    if (k < j1 && j1 < i) {
      int e = j1 + h[j1];
      if (e == i) {
        used.insert(Triple(i, j1, k));
      }
    }
    if (k < j2 && j2 < i) {
      int e = j2 - h[j2];
      if (e == k) {
        used.insert(Triple(i, j2, k));
      }
    }
  }

  // for (auto &el : used) {
  //   cerr << el.i << " " << el.j << " " << el.k << "\n";
  // }
  return sz(used);
}

ll count_triples(vi h) {
  int n = sz(h);
  
  ll ans = 0;
  FOR(i, 0, n) {
    FOR(j, 0, i) {
      // for a given pair (i, j) the possible values for k are i - h[i], i - h[j], j+h[i], j+h[j]
      int dist = i - j;
      vi K = {i-h[i], i-h[j], j+h[i], j+h[j]};
      set<int> seen;

      each(k, K) {
        if (!(j < k && k < i)) continue;
        if (seen.count(k)) continue;
        seen.insert(k);

        vi d = {abs(i-j), abs(i-k), abs(j-k)}, f = {h[i], h[j], h[k]};
        srt(d); srt(f);
        bool valid = d[0] == f[0] && d[1] == f[1] && d[2] == f[2];
        if (!valid) continue;

        ans++;
        // cerr << i << " " << j << " " << k << "\n";
      }
    }
  }
  return ans;
}

vi construct_range(int M, int K) {
  return {1, 1, 2, 3, 3, 1, 2, 1, 4, 3, 2, 3, 1, 2, 1, 4, 3, 2, 3, 1};
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...