在数组中查找重复的算法

时间:2010-11-16 09:34:51

标签: algorithm

我有一个分配来创建一个算法来查找包含数字值的数组中的重复项。但它没有说出哪种数字,整数或浮点数。我写了以下伪代码:

 FindingDuplicateAlgorithm(A) // A is the array
      mergeSort(A);
      for  int i <- 0 to i<A.length
           if A[i] == A[i+1]
                 i++
               return  A[i]
           else
                 i++

我创建了一个有效的算法吗? 我认为我的算法存在问题,它会多次返回重复的数字。例如,如果数组包含2对2的两个索引,我将在输出中有... 2,2,...如何更改它只返回每个重复一次? 我认为它对于整数来说是一个很好的算法,但它对浮点数也有效吗?

7 个答案:

答案 0 :(得分:11)

要处理重复项,您可以执行以下操作:

if A[i] == A[i+1]:
    result.append(A[i]) # collect found duplicates in a list
    while A[i] == A[i+1]: # skip the entire range of duplicates 
        i++               # until a new value is found

答案 1 :(得分:6)

您想在Java中找到Duplicates吗?

您可以使用HashSet。

HashSet h = new HashSet();
for(Object a:A){
   boolean b = h.add(a);
   boolean duplicate = !b;
   if(duplicate)
       // do something with a;
}

add()的返回值定义为:

  

如果尚未设置,则为true   包含指定的元素。

修改 我知道HashSet针对插入进行了优化并包含操作。但是我不确定它是否足以让你担心。

<强> EDIT2: 我见过你最近添加了家庭作业标签。我不喜欢我的答案,如果它是家庭作业,因为它可能是“高级”的算法课程

http://download.oracle.com/javase/1.4.2/docs/api/java/util/HashSet.html#add%28java.lang.Object%29

答案 2 :(得分:2)

你的答案似乎很好。首先排序并简单地检查相邻值会给你O(n log(n))复杂性,这非常有效。

合并排序为O(n log(n)),而检查邻近值只是O(n)

但有一件事(正如其中一条评论中提到的那样)你将得到一个带有伪代码的堆栈溢出(lol)。内循环应该是(在Java中):

for (int i = 0; i < array.length - 1; i++) {
    ...
}

然后,如果您确实想要显示哪些数字(和/或索引)是重复项,则需要将它们存储在单独的列表中。

答案 3 :(得分:1)

我不确定你需要用什么语言来编写算法,但是这里有一些非常好的C ++解决方案来响应my question。应该对你有用。

答案 4 :(得分:1)

O(n)算法:遍历数组并尝试在哈希表/集合中输入每个元素,并将数字作为哈希键。如果你不能进入,那就是重复。

答案 5 :(得分:1)

 public void printDuplicates(int[] inputArray) {
    if (inputArray == null) {
        throw new IllegalArgumentException("Input array can not be null");
    }
    int length = inputArray.length;

    if (length == 1) {
        System.out.print(inputArray[0] + " ");
        return;
    }

    for (int i = 0; i < length; i++) {

        if (inputArray[Math.abs(inputArray[i])] >= 0) {
            inputArray[Math.abs(inputArray[i])] = -inputArray[Math.abs(inputArray[i])];
        } else {
            System.out.print(Math.abs(inputArray[i]) + " ");
        }
    }
}

答案 6 :(得分:0)

您的算法包含缓冲区溢出。 i以0开头,因此我假设数组A中的索引是从零开始的,即第一个元素是A[0],最后一个是A[A.length-1]。现在i计数到A.length-1,并且在循环体中访问A[i+1],它在最后一次迭代的数组之外。或者,简单地说:如果您将每个元素与下一个元素进行比较,则只能进行长度为1的比较。

如果您只想报告重复一次,我会使用bool变量firstDuplicate,当您找到重复时设置为false,当数字与下一个不同时设置为true。然后,只有在firstDuplicate为真时才报告重复的数字,您才会报告第一个副本。