在一个由 m 个用户组成的社交网络里,我们获取到一些用户之间的好友关系。两个用户之间可以相互沟通的条件是他们都掌握同一门语言。
给你一个整数 n ,数组 languages 和数组 friendships ,它们的含义如下:
总共有 n 种语言,编号从 1 到 n 。
languages[i] 是第 i 位用户掌握的语言集合。
friendships[i] = [ui, vi] 表示 ui 和 vi 为好友关系。
你可以选择 一门 语言并教会一些用户,使得所有好友之间都可以相互沟通。请返回你 最少 需要教会多少名用户。
请注意,好友关系没有传递性,也就是说如果 x 和 y 是好友,且 y 和 z 是好友, x 和 z 不一定是好友。
输入:n = 2, languages = [[1],[2],[1,2]], friendships = [[1,2],[1,3],[2,3]]
输出:1
解释:你可以选择教用户 1 第二门语言,也可以选择教用户 2 第一门语言。
class Solution {
public int minimumTeachings(int n, int[][] languages, int[][] friendships) {
Set[] sets = new HashSet[n+1];//每种语言已经会的人的集合
Set[] arr = new HashSet[n+1]; //每种语言需要教的人的集合
int min = Integer.MAX_VALUE;
for (int i = 0; i < sets.length; i ++) {
sets[i] = new HashSet();
arr[i] = new HashSet();
}
//先找出每种语言哪些人已经学会了
for (int i = 0; i < languages.length; i ++) {
for (int j = 0 ; j < languages[i].length; j ++) {
sets[languages[i][j]].add(i+1);
}
}
//遍历朋友关系
out:
for (int i = 0; i < friendships.length; i ++) {
//如果两个人已经可以交流,不需要再教,跳过
for (int j = 1; j < sets.length; j ++) {
if (sets[j].contains(friendships[i][0]) && sets[j].contains(friendships[i][1]) ) {
continue out;
}
}
//如果不能交流,需要学习新语言
for (int j = 1; j < sets.length; j ++) {
if (!sets[j].contains(friendships[i][0])) {
arr[j].add(friendships[i][0]);
}
if (!sets[j].contains(friendships[i][1])) {
arr[j].add(friendships[i][1]);
}
}
}
//找出最小值
for (int i = 1; i < arr.length; i ++) {
min = Math.min(min, arr[i].size());
}
return min;
}
}
先找出每种语言哪些人已经学会了,再找出为了维持朋友关系,每种语言分别需要教哪些人(如果已经学会了就不需要再教了),取各个语言需要教的人数的最小值。