There are n people whose IDs go from 0 to n - 1 and each person belongs exactly to one group. Given the array groupSizes of length n telling the group size each person belongs to, return the groups there are and the people’s IDs each group includes.
You can return any solution in any order and the same applies for IDs. Also, it is guaranteed that there exists at least one solution.
Example 1:
Input: groupSizes = [3,3,3,3,3,1,3] Output: [[5],[0,1,2],[3,4,6]] Explanation: Other possible solutions are [[2,1,6],[5],[0,4,3]] and [[5],[0,6,2],[4,3,1]].
Example 2:
Input: groupSizes = [2,1,3,3,3,2] Output: [[1],[0,5],[2,3,4]]
Constraints:
groupSizes.length == n
1 <= n <= 500
1 <= groupSizes[i] <= n
题意:groupSizes中的数字表示:当前这个人所属的组的总人数。 [2,1,3,3,3,2]意思是 0号ID所属组的人数为2 1号ID所属组的人数为1 2号ID所属组的人数为3 3号ID所属组的人数为3 4号ID所属组的人数为3 5号ID所属组的人数为2
显然,0和5为一组,1单人一组,2,3,4为一组 所以结果为[[0,5],[1],[2,3,4]]
分析:
算法:
1. 将groupSize中相同的值的"下标"放在一个数组中;
2. 如果“相同的值的个数”等于“相同值”,就把该数组加到结果集;
否则:
创建“相同值的个数/2”个数组,将下标均分在这些数组中,加入结果集;
3. 返回结果集
如何完成第一步?其实跟“找出数组中的所有相同值”方法一样:
遍历groupSize,如果groupSizes[i]==x,将i加入tmp数组中,直到i=groupSizes.length;最后返回该tmp数组
如何完成“下标均分”?
以[2,2,2,2]为例:
创建“相同值的个数/groupSizes[i]”个数组 --> 创建2个数组
每组均分“相同值”个数组 --> 即每组均分2个数据,[0,1] [2,3]
这个算法有个错误,我改不出来。
返回的结果是正确的,但是多了,个数等于n * tmp.size() / groupSizes[i]; 我试了试把创建tmp单独放在外面,个数为groupSizes去重后的大小,然而仍然不正确。
class Solution {
public List<List<Integer>> groupThePeople(int[] groupSizes) {
List<List<Integer>> res = new ArrayList<>();
int n = groupSizes.length;
int i=0;
while(i<n){
List<Integer> tmp = search(groupSizes[i],groupSizes);
int k=0;
if(tmp.size()==groupSizes[i])
res.add(tmp);
else{
for(int j=0;j<tmp.size()/groupSizes[i];++j){
List<Integer> tmp2 = new ArrayList<>();
int flag=groupSizes[i];
while(flag>0){
tmp2.add(tmp.get(k++));
flag--;
}
res.add(tmp2);
}
k=0;
}
i++;
}
return res;
}
// 返回所有相同组数的下标(组员)
public List<Integer> search(int x,int[] groupSizes){
List<Integer> tmp = new ArrayList<>();
for(int i=0;i<groupSizes.length;++i){
if(x==groupSizes[i])
tmp.add(i);
}
return tmp;
}
}
看看评论区答案,算法类似,但是通过Map,更加简单。
class Solution {
public List<List<Integer>> groupThePeople(int[] groupSizes) {
// 存放结果集
List<List<Integer>> res=new ArrayList<>();
// key:组成员数,value:所有组员
Map<Integer, List<Integer>> map=new HashMap<>();
for(int i=0;i<groupSizes.length;i++) {
// 如果map中不存在这个成员组数,就加到map中
if(!map.containsKey(groupSizes[i])) map.put(groupSizes[i], new ArrayList<>());
// 获取当前成员小组
List<Integer> cur=map.get(groupSizes[i]);
// 把当前成员加到小组中
cur.add(i);
// 如果当前组成员数等于实际组成员数
if(cur.size()==groupSizes[i]) {
res.add(cur);
// 将当前组移除
map.remove(groupSizes[i]);
}
// 如果当前组成员数不等于实际组成员数,也就是分析中算法的第二种情况,此时回到循环开头map.containsKey判断就不成立,就不会创建新的list。通过这种方式,解决了我上述算法的问题。
}
return res;
}
}
扫码关注腾讯云开发者
领取腾讯云代金券
Copyright © 2013 - 2025 Tencent Cloud. All Rights Reserved. 腾讯云 版权所有
深圳市腾讯计算机系统有限公司 ICP备案/许可证号:粤B2-20090059 深公网安备号 44030502008569
腾讯云计算(北京)有限责任公司 京ICP证150476号 | 京ICP备11018762号 | 京公网安备号11010802020287
Copyright © 2013 - 2025 Tencent Cloud.
All Rights Reserved. 腾讯云 版权所有