Codeforces Round #422 (Div. 2) C. Hacker, pack your bags! [二分]
传送门:http://codeforces.com/contest/822/problem/C
题意:找两端互不相交的线段长度和为x 使cost最小
直接排序后二分搜对应的长度内的最小值。也可以边查询边更新对应长度最小值,复杂度相同。代码如下:
1 #define _CRT_SECURE_NO_DEPRECATE 2 #pragma comment(linker, "/STACK:102400000,102400000") 3 #include<iostream> 4 #include<cstdio> 5 #include<fstream> 6 #include<iomanip> 7 #include<algorithm> 8 #include<cmath> 9 #include<deque> 10 #include<vector> 11 #include<assert.h> 12 #include<bitset> 13 #include<queue> 14 #include<string> 15 #include<cstring> 16 #include<map> 17 #include<stack> 18 #include<set> 19 #include<functional> 20 #define pii pair<int, int> 21 #define mod 1000000007 22 #define mp make_pair 23 #define pi acos(-1) 24 #define eps 0.00000001 25 #define mst(a,i) memset(a,i,sizeof(a)) 26 #define all(n) n.begin(),n.end() 27 #define lson(x) ((x<<1)) 28 #define rson(x) ((x<<1)|1) 29 #define inf 0x3f3f3f3f 30 typedef long long ll; 31 typedef unsigned long long ull; 32 using namespace std; 33 34 const int maxn = 2e5 + 5; 35 36 class T{ 37 public: 38 int l, r, c; 39 }; 40 T sve[maxn]; 41 42 bool operator<(const T&a, const T&b) { return a.l < b.l; } 43 vector<T>a[maxn]; 44 vector<int>sv[maxn]; 45 int main() 46 { 47 ios::sync_with_stdio(false); 48 cin.tie(0); cout.tie(0); 49 int i, j, k, m, n; 50 cin >> n >> m; 51 for (int i = 1; i <= n; ++i) 52 { 53 cin >> sve[i].l >> sve[i].r >> sve[i].c; 54 a[sve[i].r - sve[i].l + 1].push_back(sve[i]); 55 } 56 ll ansc = 100000000000LL; 57 for(int i=1;i<=200000;++i) 58 if (!a[i].empty()) 59 sort(all(a[i])); 60 int flag = 0; 61 for (int i = 1; i <= 200000; ++i) 62 if (!a[i].empty()) 63 { 64 sv[i].resize(a[i].size()); 65 int tmp = a[i].size() - 1; 66 sv[i][tmp] = a[i][tmp].c; 67 for (int j = sv[i].size() - 2; j >= 0; --j) 68 sv[i][j] = min(a[i][j].c, sv[i][j + 1]); 69 } 70 for (int i = 1; i <= n; ++i) 71 { 72 int cas = m - (sve[i].r - sve[i].l + 1); 73 if (cas <= 0)continue; 74 T tmp = { sve[i].r,0,0 }; 75 int pos = upper_bound(a[cas].begin(), a[cas].end(), tmp) - a[cas].begin(); 76 if (pos == a[cas].size())continue; 77 else 78 { 79 ll sumc = sve[i].c + sv[cas][pos]; 80 if (ansc > sumc) 81 { 82 ansc = sumc; 83 flag = 1; 84 } 85 } 86 } 87 if (flag)cout << ansc; 88 else cout << "-1"; 89 return 0; 90 }