题意:有b块钱,想要组装一台电脑,给出n个配件的种类,名字,价格,品质因子。若各种类配件各买一个,总价格<=b,求最差品质配件的最大品质因子。
思路:
求最大的最小值一般用二分法。
在(0,maxq)内进行二分,判定q作为最差品质因子是否可行。
大白书原题,比较考验代码功底。
code:
/* * @author Novicer * language : C++/C */ #include<iostream> #include<sstream> #include<fstream> #include<vector> #include<list> #include<deque> #include<queue> #include<stack> #include<map> #include<set> #include<bitset> #include<algorithm> #include<cstdio> #include<cstdlib> #include<cstring> #include<cctype> #include<cmath> #include<ctime> #include<iomanip> using namespace std; const double eps(1e-8); typedef long long lint; const int maxn = 1000 + 5; map<string,int> id; int n,b; int cnt = 0; struct Comp{ int price; int quality; }; vector<Comp> comp[maxn]; int ID(string s){ if(!id.count(s)){ id[s] = cnt++; } return id[s]; } bool ok(int q){ int sum = 0; // cout << q << endl; for(int i = 0 ; i < cnt ; i++){ int cheapest = b + 1; for(int j = 0 ; j < comp[i].size() ; j++){ // cout << comp[i][j].price << endl; if(q <= comp[i][j].quality) cheapest = min(cheapest , comp[i][j].price); } if(cheapest == b+1) return false; sum += cheapest; // cout << "q : " << q << " sum : " << sum << endl; if(sum > b) return false; } return true; } int solve(int l , int r){ while(l < r){ int m = l + (r - l + 1)/2; if(ok(m)) l = m; else r = m - 1; // cout << m << endl; } return l; } int main(){ // freopen("input.txt","r",stdin); int T; cin >> T; while(T--){ cnt = 0; cin >> n >> b; for(int i = 0 ; i < n ; i++) comp[i].clear(); int maxq = 0; for(int i = 1 ; i <= n ; i++){ string type,name; int p,q; cin >> type >> name >> p >> q; // cout << type << name << p << q << endl; maxq = max(maxq , q); Comp tmp; tmp.price = p; tmp.quality = q; comp[ID(type)].push_back(tmp); } // cout << maxq << endl; int L = 0 , R = maxq; int ans = solve(L,R); cout << ans << endl; } return 0; }
版权声明:本文为博主原创文章,未经博主允许不得转载。
UVALive 3971 Assemble(模拟 + 二分)
原文地址:http://blog.csdn.net/qq_15714857/article/details/47062087