1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59
| struct Seg { int mi, ma, cnt, id; Seg *left, *right; Seg(vector<int>& A, int l, int r) : mi(A[l]), ma(A[r]), cnt(0), id(0), left(nullptr), right(nullptr) { if(l^r) { int m = l + (r - l) / 2; left = new Seg(A,l,m); right = new Seg(A,m+1,r); } } void validate(int seq) { if(id == seq) return; id = seq; cnt = 0; } int query(int l, int r, int seq) { validate(seq); if(l <= mi and ma <= r) return cnt; if(l > ma or r < mi) return 0; return left->query(l,r,seq) + right->query(l,r,seq); } void update(int n, int seq) { validate(seq); if(mi <= n and n <= ma) { cnt++; if(left) left->update(n,seq); if(right) right->update(n,seq); } } }; class Solution { int seq; int helper(vector<int>& A, Seg* seg, int m) { int res = 0; for(auto& n : A) { res += seg->query(n + 1, n + m, seq); seg->update(n,seq); } return res; } public: int minThreshold(vector<int>& nums, int k) { auto S = nums; sort(begin(S), end(S)); S.erase(unique(begin(S), end(S)), end(S)); Seg* seg = new Seg(S,0,S.size() - 1); int l = 1, r = 1e9, res = INT_MAX; while(l <= r) { int m = l + (r - l) / 2; bool ok = helper(nums,seg,m) >= k; if(ok) { res = m; r = m - 1; } else l = m + 1; seq++; } return res == INT_MAX ? -1 : res; } };
|