【网易】牛牛找工作

https://www.nowcoder.com/practice/46e837a4ea9144f5ad2021658cb54c4d?tpId=98&tqId=32824&tPage=1&rp=1&ru=/ta/2019test&qru=/ta/2019test/question-ranking

  为了找到自己满意的工作,牛牛收集了每种工作的难度和报酬。牛牛选工作的标准是在难度不超过自身能力值的情况下,牛牛选择报酬最高的工作。在牛牛选定了自己的工作后,牛牛的小伙伴们来找牛牛帮忙选工作,牛牛依然使用自己的标准来帮助小伙伴们。牛牛的小伙伴太多了,于是他只好把这个任务交给了你。 

  输入描述
 每个输入包含一个测试用例。
每个测试用例的第一行包含两个正整数,分别表示工作的数量N(N<=100000)和小伙伴的数量M(M<=100000)。
接下来的N行每行包含两个正整数,分别表示该项工作的难度Di(Di<=1000000000)和报酬Pi(Pi<=1000000000)。
接下来的一行包含M个正整数,分别表示M个小伙伴的能力值Ai(Ai<=1000000000)。
保证不存在两项工作的报酬相同。
  输出描述
  对于每个小伙伴,在单独的一行输出一个正整数表示他能得到的最高报酬。一个工作可以被多个人选择。
  输入例子1
  3 3 
  1 100 
  10 1000 
  1000000000 1001 
  9 10 1000000000
  输出例子1
  100 
  1000 
  1001

暴力法

  时间复杂度:O(N*M)。

  空间复杂度:O(N+M)。

 1 #include <iostream>
 2 #include <vector>
 3 
 4 using namespace std;
 5 
 6 int main()
 7 {
 8     //输入数据
 9     int N, M;
10     cin >> N >> M;
11     vector<int> difficulty(N), profit(N), ability(M);
12     int i = 0;
13     while (i < N)
14     {   
15        cin >> difficulty[i] >> profit[i];
16         i++;
17     }
18     int j = 0;
19     while (j < M)
20     {
21         cin >> ability[j];
22         j++;
23     }
24     //解决问题
25     for (const auto Ai : ability)
26     {
27         int maxPay = 0;
28         for (int j = 0; j < N; ++j)
29         {
30             if (Ai >= difficulty[j])
31                 maxPay = max(maxPay, profit[j]);
32         }
33         cout << maxPay << endl;
34     }
35     return 0;
36 }

排序+双指针

  

    思路:工人i能做的工作,能力比他高的工人i+1一定能做,换句话说工人i+1的最大薪酬至少是i的最大薪酬。我们只需要把i的最大薪酬和i+1的另外可以胜任的工作薪酬比较取最大即可。使用双指针来分别定位已经访问过的工作和工人。

   时间复杂度:O(N*logN + M*logM)。分别对工作排序时间复杂度我O(N*logN),对工人排序时间复杂度为O(M*logM)。最后的比较时间复杂度为O(M + N),因为每个元素都只遍历1次。

  空间复杂度:O(N + M)。

 1 #include <iostream>
 2 #include <vector>
 3 #include <numeric> //for iota()
 4 #include <algorithm> // for sort()
 5 #include <iterator> //ostream_iterator<T>
 6 
 7 using namespace std;
 8 
 9 int main()
10 {
11     //输入数据
12     int N, M;
13     cin >> N >> M;
14     vector<int> difficulty(N), profit(N), ability(M);
15     int i = 0;
16     while (i < N)
17     {   
18        cin >> difficulty[i] >> profit[i];
19         i++;
20     }
21     i = 0;
22     while (i < M)
23     {
24         cin >> ability[i];
25         i++;
26     }
27     //解决问题
28     //记录工作难度和工人能力值索引
29     vector<int> difficulty_index(difficulty.size()), ability_index(ability.size());
30     iota(difficulty_index.begin(), difficulty_index.end(), 0);
31     iota(ability_index.begin(), ability_index.end(), 0);
32     // 排序
33     //O(N*logN)
34     sort(difficulty_index.begin(), difficulty_index.end(), [&] (int a, int b) {return difficulty[a] < difficulty[b]; });
35    //O(M*logM)
36     sort(ability_index.begin(), ability_index.end(), [&] (int a, int b) {return ability[a] < ability[b]; });
37 
38     vector<int> ans(M, 0);
39     int maxPay = 0;
40     int j = 0;      //工作难度指针
41     //O(M + N)
42     for (int i = 0; i < M; ++i) //工人能力指针
43     {
44         while (j < N && difficulty[difficulty_index[j]] <= ability[ability_index[i]])
45             maxPay = max(maxPay, profit[difficulty_index[j++]]);
46         ans[ability_index[i]] = maxPay;   
47     }
48     //输出结果  
49     copy(ans.begin(), ans.end(), ostream_iterator<int>(cout, "\n"));
50     return 0;
51 }

猜你喜欢

转载自www.cnblogs.com/chen-cs/p/12905501.html