来自三个给定集合的两个集合的交集?

时间:2019-10-07 16:43:06

标签: java set

我必须编写一种算法,可以从三个给定的集合中找到两个集合的交集。例如,如果该元素存在于三个集合中的两个集合中,则表示很好,但是如果该元素存在于所有三个集合中,则不应添加该元素

3 个答案:

答案 0 :(得分:0)

  1. 创建哈希图
  2. 遍历每个集合,如果键尚未在哈希图中,则将元素添加为值为1的元素,如果哈希图中的键将值增加1。
  3. 遍历hashmap并使用值为2的键创建结果集。

答案 1 :(得分:0)

一个好的解决方案是将所有集合集合在一起,计算每个元素的频率,并只保留出现两次的元素

使用流

  • 具有3组的流
  • 三个集合中所有元素的串联流
  • 建立地图
  • 重复配对
  • 保留值== 2的那些
  • 仅保留钥匙
  • 收集到一个集合
static <T> Set<T> intersectionTwoButNotThree(Set<T> s1, Set<T> s2, Set<T> s3) {
    return Stream.of(s1, s2, s3)
            .flatMap(Set::stream)
            .collect(Collectors.groupingBy(Function.identity(), Collectors.counting()))
            .entrySet()
            .stream()
            .filter(entry -> entry.getValue() == 2)
            .map(Map.Entry::getKey)
            .collect(Collectors.toSet());
}

有循环

static <T> Set<T> intersectionTwoButNotThree(Set<T> s1, Set<T> s2, Set<T> s3) {
    Map<T, Integer> map = new HashMap<>();
    for (T elt : s1) 
        map.merge(elt, 1, Integer::sum); // sum previous value and 1
    for (T elt : s2) 
        map.merge(elt, 1, Integer::sum); // sum previous value and 1
    for (T elt : s3) 
        map.merge(elt, 1, Integer::sum); // sum previous value and 1

    Set<T> set = new HashSet<>();
    for (Map.Entry<T, Integer> e : map.entrySet()) 
        if (e.getValue() == 2) 
            set.add(e.getKey());

    return set;
}

答案 2 :(得分:0)

下面是我的尝试

public class Test {

    List<Set> sets = new ArrayList<>();
    Set<String> one = new HashSet<>();
    Set<String> two = new HashSet<>();
    Set<String> thr = new HashSet<>();

    enum EStatus{
        IT_IS_GOOD,
        SHOULD_NOT_BE_ADDED,
        EPIC_FAIL
    }

    public static void main(String[] args) {
        Test mainT = new Test();
        mainT.prepareData();
        System.out.println(mainT.doStuff("three"));
    }


    public EStatus doStuff(String element){
        for(int i = 1; i <= 3; i++){
            Set<String> intersectionOfTwo = new HashSet<>(sets.get(i-1));
            intersectionOfTwo.retainAll(sets.get(i % 3));
            if(intersectionOfTwo.contains(element)){
                Set<String> intersectionOfThree  = new HashSet<>(intersectionOfTwo);
                intersectionOfThree.retainAll(sets.get((i + 1) % sets.size()));
                if(intersectionOfThree.contains(element)){
                    return EStatus.SHOULD_NOT_BE_ADDED;
                }else{
                    return EStatus.IT_IS_GOOD;
                }
            }
        }
        return EStatus.EPIC_FAIL;
    }

    public void prepareData(){
        one.add("one");
        one.add("two");
        one.add("three");
        two.add("two");
        two.add("three");
        thr.add("three");
        thr.add("four");
        sets.add(one);
        sets.add(two);
        sets.add(thr);
    }
}