題意node
在二維平面有\(n\)個海盜,\(m\)個探照燈,你有兩種操做ios
設海盜爲\((a_i,b_i)\),探照燈爲\((c_j,d_j)\),當且僅當\(a_i\leq c_j\)且\(b_i\leq d_j\)時,海盜在探照燈範圍內,問最少多少次操做能夠將全部海盜移動到全部探照燈範圍外c++
分析spa
將題意抽象一下,找到一個二元組\((x,y)\),\(x\)表示向上走的步數,\(y\)表示向右走的步數,而後對於任何海盜\((a_i,b_i)\),都知足加上\((x,y)\)後,對於任何探照燈\((c_j,d_j)\)要麼\(a_i+x>c_j\),要麼\(b_i+y>d_j\),且\(x+y\)最小code
那麼咱們\(O(nm)\)處理,找到海盜和探照燈之間的關係,若海盜在探照燈範圍內,獲得二元組\((x,y)\),有\(a_i+x>c_j\)且\(b_i+y>d_j\),獲得全部二元組後,按照第一維排序排序
此時發現,遍歷二元組,遍歷到第\(i\)個二元組時,若是取該二元組的\(x\),那麼\(y\)最小即爲剩餘二元組的最大值,這樣能夠知足前部分探照燈向上走便可脫離,剩餘探照燈向右走便可脫離,注意答案初始值是隻往右走時的答案ci
#pragma GCC optimize(3, "Ofast", "inline") #include <bits/stdc++.h> #define start ios::sync_with_stdio(false);cin.tie(0);cout.tie(0); #define ll long long #define int ll #define ls st<<1 #define rs st<<1|1 #define pii pair<int,int> #define rep(z, x, y) for(int z=x;z<=y;++z) #define repd(z, x, y) for(int z=x;z>=y;--z) #define com bool operator<(const node &b)const using namespace std; mt19937 rnd(chrono::high_resolution_clock::now().time_since_epoch().count()); const int maxn = (ll) 3e5 + 5; const int mod = 998244353; const int inf = 0x3f3f3f3f; int T = 1; pii a[2005], b[2005]; int maxx[2005 * 2005]; void solve() { int n, m; cin >> n >> m; rep(i, 1, n)cin >> a[i].first >> a[i].second; rep(i, 1, m)cin >> b[i].first >> b[i].second; vector<pii > v; rep(i, 1, n) { rep(j, 1, m) { if (b[j].first < a[i].first || b[j].second < a[i].second) continue; v.push_back({max(b[j].first + 1 - a[i].first, 0ll), max(0ll, b[j].second + 1 - a[i].second)}); } } if (v.empty()) { cout << 0; return; } sort(v.begin(), v.end()); for (int i = v.size() - 1; i >= 0; --i)maxx[i] = max(maxx[i + 1], v[i].second); int ans = maxx[0]; for (int i = 0; i < v.size(); ++i)ans = min(ans, v[i].first + maxx[i + 1]); cout << ans; } signed main() { start; while (T--) solve(); return 0; }