首页 > 代码库 > ecjtu-summer training #11
ecjtu-summer training #11
A - Fence Repair
Farmer John wants to repair a small length of the fence around the pasture. He measures the fence and finds that he needs N (1 ≤ N ≤ 20,000) planks of wood, each having some integer length Li (1 ≤ Li ≤ 50,000) units. He then purchases a single long board just long enough to saw into the N planks (i.e., whose length is the sum of the lengths Li). FJ is ignoring the "kerf", the extra length lost to sawdust when a sawcut is made; you should ignore it, too.
FJ sadly realizes that he doesn‘t own a saw with which to cut the wood, so he mosies over to Farmer Don‘s Farm with this long board and politely asks if he may borrow a saw.
Farmer Don, a closet capitalist, doesn‘t lend FJ a saw but instead offers to charge Farmer John for each of the N-1 cuts in the plank. The charge to cut a piece of wood is exactly equal to its length. Cutting a plank of length 21 costs 21 cents.
Farmer Don then lets Farmer John decide the order and locations to cut the plank. Help Farmer John determine the minimum amount of money he can spend to create the N planks. FJ knows that he can cut the board in various different orders which will result in different charges since the resulting intermediate planks are of different lengths.
Lines 2.. N+1: Each line contains a single integer describing the length of a needed plank
3 8 5 8Sample Output
34
优先队列,水题。
1 #include <iostream> 2 #include <stdio.h> 3 #include <string.h> 4 #include <algorithm> 5 #include <queue> 6 #include <vector> 7 using namespace std; 8 #define ll long long 9 int main(){ 10 ll n,num; 11 priority_queue<ll, vector<ll>, greater<ll> >que; 12 cin>>n; 13 for(int i = 1; i <= n; i ++)cin>>num,que.push(num); 14 if(que.size()==1){ 15 cout << 0 << endl; 16 return 0; 17 } 18 ll sum = 0; 19 while(que.size() != 1){ 20 ll a = que.top(); 21 que.pop(); 22 ll cnt = que.top(); 23 que.pop(); 24 ll ans = a+cnt; 25 sum+=ans; 26 que.push(ans); 27 } 28 cout << sum << endl; 29 return 0; 30 }
B - A Bug‘s Life
Description
Professor Hopper is researching the sexual behavior of a rare species of bugs. He assumes that they feature two different genders and that they only interact with bugs of the opposite gender. In his experiment, individual bugs and their interactions were easy to identify, because numbers were printed on their backs.
Problem
Given a list of bug interactions, decide whether the experiment supports his assumption of two genders with no homosexual bugs or if it contains some bug interactions that falsify it.
Input
Output
Sample Input
2 3 3 1 2 2 3 1 3 4 2 1 2 3 4
Sample Output
Scenario #1: Suspicious bugs found! Scenario #2: No suspicious bugs found!
带权并查集,数组开两倍大小,这样就可以用两个集合了,相对的就是x,y+N,和x+N,y。一个集合就是x,y和x+N,y+N。
1 #include <iostream> 2 #include <string.h> 3 #include <stdio.h> 4 #include <algorithm> 5 #define ll long long 6 using namespace std; 7 const int MAX = 2010; 8 const int N = 1000010; 9 int a[MAX], fa[N*2]; 10 int find(int x) { 11 return fa[x] = (fa[x] == x) ? x : find(fa[x]); 12 } 13 int unite(int x, int y) { 14 x = find(x); 15 y = find(y); 16 if(x < y) fa[y] = x; 17 else fa[x] = y; 18 } 19 int main() { 20 int t, n, m; 21 scanf("%d",&t); 22 for(int k = 1; k <= t; k ++) { 23 scanf("%d%d",&n,&m); 24 for(int i = 0; i < N*2; i ++) fa[i] = i; 25 bool flag = true; 26 for(int i = 1; i <= m; i ++) { 27 int x, y; 28 scanf("%d%d",&x,&y); 29 if(!flag)continue; 30 x = find(x),y = find(y); 31 if(x == y) flag = false; 32 else { 33 unite(x,N+y); 34 unite(x+N,y); 35 } 36 } 37 if(k!=1)printf("\n"); 38 printf("Scenario #%d:\n",k); 39 if(flag) printf("No suspicious bugs found!\n"); 40 else printf("Suspicious bugs found!\n"); 41 } 42 return 0; 43 }
C - Jessica‘s Reading Problem
Jessica‘s a very lovely girl wooed by lots of boys. Recently she has a problem. The final exam is coming, yet she has spent little time on it. If she wants to pass it, she has to master all ideas included in a very thick text book. The author of that text book, like other authors, is extremely fussy about the ideas, thus some ideas are covered more than once. Jessica think if she managed to read each idea at least once, she can pass the exam. She decides to read only one contiguous part of the book which contains all ideas covered by the entire book. And of course, the sub-book should be as thin as possible.
A very hard-working boy had manually indexed for her each page of Jessica‘s text-book with what idea each page is about and thus made a big progress for his courtship. Here you come in to save your skin: given the index, help Jessica decide which contiguous part she should read. For convenience, each idea has been coded with an ID, which is a non-negative integer.
The first line of input is an integer P (1 ≤ P ≤ 1000000), which is the number of pages of Jessica‘s text-book. The second line contains P non-negative integers describing what idea each page is about. The first integer is what the first page is about, the second integer is what the second page is about, and so on. You may assume all integers that appear can fit well in the signed 32-bit integer type.
Output one line: the number of pages of the shortest contiguous part of the book which contains all ideals covered in the book.
5 1 8 8 8 1Sample Output
2
贪心,先让l和r等于1,然后r++,在[l,r]区间内,如果全部包括了,就从a[l]开始便利只要a[l]出现次数大于1就l++。每次满足保存一个最新值。
1 #include <iostream> 2 #include <string.h> 3 #include <stdio.h> 4 #include <algorithm> 5 #include <map> 6 #include <set> 7 #define ll long long 8 using namespace std; 9 const int MAX = 1000010; 10 int a[MAX]; 11 map<int,int> mp; 12 set<int> st; 13 int main() { 14 int p; 15 while(scanf("%d",&p) !=EOF) { 16 for(int i = 1; i <= p; i ++) { 17 scanf("%d",&a[i]); 18 st.insert(a[i]); 19 } 20 int k = st.size(); 21 st.clear(); 22 int l = 1, r = 1, minn = MAX*10; 23 while(r <= p) { 24 st.insert(a[r]); 25 mp[a[r]] ++; 26 if(st.size() == k) { 27 while(mp[a[l]] >= 2) { 28 mp[a[l]]--;l++; 29 } 30 if(r-l+1 < minn) minn = r-l+1; 31 } 32 r++; 33 } 34 printf("%d\n",minn); 35 st.clear(); 36 mp.clear(); 37 memset(a,0,sizeof(a)); 38 } 39 return 0; 40 }
D - Communication System
Description
By overall bandwidth (B) we mean the minimum of the bandwidths of the chosen devices in the communication system and the total price (P) is the sum of the prices of all chosen devices. Our goal is to choose a manufacturer for each device to maximize B/P.
Input
Output
Sample Input
1 3 3 100 25 150 35 80 25 2 120 80 155 40 2 100 100 120 110
Sample Output
0.649
英语渣渣的我看了大半个小时才看懂。用贪心来做,取每个设备的宽带的最大值,在这些最大值的宽带里取最小的那个当成总宽带,然后遍历全部,让价格加上每个设备的宽带大于总宽带的最小价格。
1 #include <iostream> 2 #include <string.h> 3 #include <stdio.h> 4 #include <algorithm> 5 #include <vector> 6 #define ll long long 7 using namespace std; 8 const double ef = 1e-9; 9 const int MAX = 11000; 10 vector<pair<double,double> >vs[MAX]; 11 int main() { 12 int t, n, m; 13 ios::sync_with_stdio(false); 14 cin>>t; 15 while(t--) { 16 cin>>n; 17 int b = 100000; 18 for(int i = 1; i <= n; i ++) { 19 cin >> m; 20 int MM = -1; 21 for(int j = 1; j <= m; j ++) { 22 double x, y; 23 cin >> x >> y; 24 if(x > MM) MM = x; 25 vs[i].push_back(make_pair(x,y)); 26 } 27 if(MM < b) b = MM; 28 } 29 double p = 0.0; 30 for(int i = 1; i <= n; i ++) { 31 double pp = 100000; 32 for(int j = 0; j < vs[i].size(); j ++) { 33 if(vs[i][j].first >= b){ 34 if(pp > vs[i][j].second) pp = vs[i][j].second; 35 } 36 } 37 // cout << pp << endl; 38 p += pp; 39 } 40 printf("%.3f\n",b/p); 41 //cout << b<< ‘ ‘ << p << endl; 42 for(int i = 1; i <= n; i ++) vs[i].clear(); 43 } 44 return 0; 45 }
E - Telephone Lines
Description
Farmer John wants to set up a telephone line at his farm. Unfortunately, the phone company is uncooperative, so he needs to pay for some of the cables required to connect his farm to the phone system.
There are N (1 ≤ N ≤ 1,000) forlorn telephone poles conveniently numbered 1..N that are scattered around Farmer John‘s property; no cables connect any them. A total of P (1 ≤ P ≤ 10,000) pairs of poles can be connected by a cable; the rest are too far apart.
The i-th cable can connect the two distinct poles Ai and Bi, with length Li (1 ≤ Li ≤ 1,000,000) units if used. The input data set never names any {Ai, Bi} pair more than once. Pole 1 is already connected to the phone system, and pole N is at the farm. Poles 1 and N need to be connected by a path of cables; the rest of the poles might be used or might not be used.
As it turns out, the phone company is willing to provide Farmer John with K (0 ≤ K < N) lengths of cable for free. Beyond that he will have to pay a price equal to the length of the longest remaining cable he requires (each pair of poles is connected with a separate cable), or 0 if he does not need any additional cables.
Determine the minimum amount that Farmer John must pay.
Input
* Line 1: Three space-separated integers: N, P, and K
* Lines 2..P+1: Line i+1 contains the three space-separated integers: Ai, Bi, and Li
Output
* Line 1: A single integer, the minimum amount Farmer John can pay. If it is impossible to connect the farm to the phone company, print -1.
Sample Input
5 7 1 1 2 5 3 1 4 2 4 8 3 2 3 5 2 9 3 4 7 4 5 6
Sample Output
4
英语好渣,比赛时一直没看懂题意,赛后才知道是求每个方案中总长度最大的最小数。
比如第一组数据走1->2->5 分别是5 9k是1 ,9去掉,答案就是5 走1->3->2->5 分别是4 3 9 , 9去掉答案是4,4比前面的5小,所以最终答案是4.
做法是dijkstra+二分来做。其实就是求最小的m使得从1到n的路径中比m大的数要小于等于k。
用数组的dijkstra会超时,这时就需要用优先队列来做了,因为数组的复杂度是:O(|V|^2),优先队列的是O(|E|log|V|)。
1 #include <iostream> 2 #include <string.h> 3 #include <stdio.h> 4 #include <algorithm> 5 #include <queue> 6 #define INF 0x3f3f3f3f 7 #define ll long long 8 using namespace std; 9 const int MAX = 1010; 10 struct Nod { 11 int to, cost; 12 }; 13 typedef pair<int,int> P; 14 int n,p,k; 15 vector<Nod> G[MAX]; 16 int d[MAX]; 17 int dij(int s, int x) { 18 priority_queue<P, vector<P>, greater<P> > que; 19 memset(d,0x3f,sizeof(d)); 20 d[s] = 0; 21 que.push(P(0,s)); 22 while(!que.empty()) { 23 P p = que.top(); que.pop(); 24 int v = p.second; 25 if(d[v] < p.first) continue; 26 for(int i = 0; i < G[v].size(); i ++) { 27 Nod e = G[v][i]; 28 int dd = d[v] + (e.cost > x ? 1 : 0); 29 if(d[e.to] > dd) { 30 d[e.to] = dd; 31 que.push(P(d[e.to],e.to)); 32 } 33 } 34 } 35 return d[n-1]; 36 } 37 int main() { 38 //ios::sync_with_stdio(false); 39 while(cin>>n>>p>>k) { 40 for(int i = 1; i <= p; i ++) { 41 int u, v, w; 42 cin >> u >> v >> w; 43 --u;--v; 44 G[u].push_back((Nod){v,w}); 45 G[v].push_back((Nod){u,w}); 46 } 47 int l = 0, r = 1000010, cnt = -1; 48 while(l <= r) { 49 int m = (l+r) >> 1; 50 int ans = dij(0,m); 51 // printf("%d %d \n",m,ans); 52 if(ans <= k){ 53 cnt = m;r = m-1; 54 }else l = m+1; 55 } 56 printf("%d\n",cnt); 57 } 58 return 0; 59 }
ecjtu-summer training #11