计算Java数组中的非重复匹配对

时间:2017-02-12 03:37:54

标签: java arrays sorting

我是java的新手,通过我的搜索在ALMOST上发现了很多关于我正在寻找但不完全的帖子。 我尝试使用基本的java技术来计算一个数字匹配的UNIQUE次数。 例如,数组{2,3,2,3,2}将具有两个唯一匹配对案例(2,2)和(3,3) 到目前为止(见下面的代码)我似乎想出的是有多少TOTAL mached对的计数。在示例情况下,结果将是四种情况(2,2),(2,2),(3,3),(2,2)。要明确这是第一学期的问题类型的东西,所以我不能使用Map或更高级的技术。带有计数和迭代的简单循环。感谢

int count = 0;
    for( int i=0;i<=hand.length-2 ;i++)
    {
        for( int j=i+1;j<=hand.length-1;j++)
        {
            if (hand[j] == hand[i])
            {

                count = count + 1;
            }
        }
    }
    System.out.println(count);

2 个答案:

答案 0 :(得分:1)

Java 8

如果您可以使用Java 8,则可以非常简单地使用流API来对元素进行分组,并检查它们中有多少属于至少一对:

    Integer[] data = { 2, 3, 2, 3, 2 };

    // create a map of each value to a list containing all instances of that value in the array
    Map<Integer, List<Integer>> map = Arrays.stream(data).collect(Collectors.groupingBy(i -> i));

    // count how many of those lists have more than one element, i.e. pairs
    long uniquePairs = map.values().stream().filter(l -> l.size() > 1).count();

    System.out.println(uniquePairs);

Java 7

如果您使用Java 7,它会更复杂,但您可以创建一个包含元素作为键的映射,以及它们作为值出现在阵列中的次数。然后,您可以遍历地图的值,查找至少出现两次的元素(即属于至少一对):

    Integer[] data = { 2, 3, 2, 3, 2 };

    // create a map of each element to a count of the times that element appears in the array
    Map<Integer, Integer> map = new HashMap<>();
    for (int i : data) {
        Integer oldCount = map.get(i);
        int newCount = oldCount == null ? 1 : oldCount + 1;
        map.put(i, newCount);
    }

    // count the number of elements that appear more than once, i.e. pairs
    int uniquePairs = 0;
    for (int i : map.values()) {
        if (i > 1) uniquePairs++;
    }

    System.out.println(uniquePairs);

答案 1 :(得分:1)

@azurefrog已经给出了一个很好的答案。这是一个实现,它计算对于给定数字具有3个以上条目的对:

List<Integer> numbers = Arrays.asList(2, 3, 2, 3, 2, 2, 9);
Map<Integer, Long> map = numbers.stream()
        .collect(Collectors.groupingBy(num -> num, Collectors.counting()))
        .entrySet()
        .stream()
        .collect(Collectors.toMap(Map.Entry::getKey, entry -> entry.getValue() / 2));

// output
map.forEach((num, count) -> System.out.println(String.format("%d has %d unique pairs", num, count)));
Long total = map.values().stream().reduce((acc, c) -> c + acc).get();
System.out.print(String.format("A total of %d pairs", total));

考虑到评论中列出的其他约束:没有修改原始数据,简单循环,只有“简单”的数据结构;

一种方法是跟踪你之前是否看过一个元素(我用布尔数组做):

int[] hand = {2,3,2,3,2,9,5,5,5,5,5,5,5};
boolean[] hasPair = new boolean[10];
for(int i = 0; i <= hand.length - 2 ; i++) {
    for(int j= i + 1; j <= hand.length - 1; j++) {
        if (hand[j] == hand[i]) {
            hasPair[hand[j]] = true;
        }
    }
}
int count = 0;
for (boolean b : hasPair) {
    if (b) {
        count += 1;
    }
}
System.out.print(count);

这会计算唯一对或'重复',假设输入数组在{1,...,9}中为int