Some people will make friend requests. The list of their ages is given and ages[i]
is the age of the ith person. html
Person A will NOT friend request person B (B != A) if any of the following conditions are true:数组
age[B] <= 0.5 * age[A] + 7
age[B] > age[A]
age[B] > 100 && age[A] < 100
Otherwise, A will friend request B.app
Note that if A requests B, B does not necessarily request A. Also, people will not friend request themselves.post
How many total friend requests are made?优化
Example 1:url
Input: [16,16] Output: 2 Explanation: 2 people friend request each other.
Example 2:spa
Input: [16,17,18] Output: 2 Explanation: Friend requests are made 17 -> 16, 18 -> 17.
Example 3:code
Input: [20,30,100,110,120] Output: Explanation: Friend requests are made 110 -> 100, 120 -> 110, 120 -> 100.
Notes:htm
1 <= ages.length <= 20000
.1 <= ages[i] <= 120
.
这道题是关于好友申请的,说是若A想要加B的好友,下面三个条件一个都不能知足才行:blog
1. B的年龄小于等于A的年龄的一半加7。
2. B的年龄大于A的年龄。
3. B大于100岁,且A小于100岁。
实际上若是你仔细看条件3,B要是大于100岁,A小于100岁,那么B必定大于A,这就跟条件2重复了,彻底不懂出题者的想法。无论了,强行解题呗。那么因为只能给比本身小的人发送好友请求,那么博主就想到咱们能够献给全部人拍个序,而后从后往前遍历,对于每一个遍历到的人,再遍历全部比他小的人,这样第二个条件就知足了,前面说了,第三个条件能够不用管了,那么只要看知足第一个条件就能够了,还有要注意的,假如两我的年龄相同,那么知足了前两个条件后,实际上是能够互粉的,因此要额外的加1,这样才不会漏掉任何一个好友申请,参见代码以下:
解法一:
class Solution { public: int numFriendRequests(vector<int>& ages) { int res = 0, n = ages.size(); sort(ages.begin(), ages.end()); for (int i = n - 1; i >= 1; --i) { for (int j = i - 1; j >= 0; --j) { if (ages[j] <= 0.5 * ages[i] + 7) continue; if (ages[i] == ages[j]) ++res; ++res; } } return res; } };
咱们能够来优化一下上面的解法,根据上面的分析,其实题目给的这三个条件能够概括成一个条件,若A想加B的好友,那么B的年龄必须在 (A*0.5+7, A] 这个范围内,因为区间要有意义的话,A*0.5+7 < A 必须成立,解出 A > 14,那么A最小就只能取15了。意思说你不能加小于15岁的好友(青少年成长保护???)。咱们的优化思路是对于每个年龄,咱们都只要求出上面那个区间范围内的个数,就是符合题意的。那么既然是求区域和,创建累加数组就是一个很好的选择了,首先咱们先创建一个统计数组numInAge,范围是[0, 120],用来统计在各个年龄点上有多少人,而后再创建累加和数组sumInAge。这个都创建好了之后,咱们就能够开始遍历,因为以前说了不能加小于15的好友,因此咱们从15开始遍历,若是某个年龄点没有人,直接跳过。而后就是统计出 (A*0.5+7, A] 这个范围内有多少人,能够经过累计和数组来快速求的,因为当前时间点的人能够跟这个区间内的全部发好友申请,而当前时间点可能还有多人,因此两者相乘,但因为咱们但区间里还包括但当前年龄点自己,因此还要减去当前年龄点上的人数,参见代码以下:
解法二:
class Solution { public: int numFriendRequests(vector<int>& ages) { int res = 0; vector<int> numInAge(121), sumInAge(121); for (int age : ages) ++numInAge[age]; for (int i = 1; i <= 120; ++i) { sumInAge[i] = numInAge[i] + sumInAge[i - 1]; } for (int i = 15; i <= 120; ++i) { if (numInAge[i] == 0) continue; int cnt = sumInAge[i] - sumInAge[i * 0.5 + 7]; res += cnt * numInAge[i] - numInAge[i]; } return res; } };
参考资料:
https://leetcode.com/problems/friends-of-appropriate-ages/