【问题标题】:Duplicates in a sorted java array已排序的 java 数组中的重复项
【发布时间】:2013-10-26 19:15:15
【问题描述】:

我必须编写一个方法,该方法接受一个已经按数字顺序排序的整数数组,然后删除所有重复的数字并返回一个仅包含没有重复的数字的数组。然后必须打印出该数组,因此我不能有任何空指针异常。该方法必须在 O(n) 时间内,不能使用向量或散列。这是我到目前为止所拥有的,但它只有前几个数字按顺序排列,没有重复,然后将重复的数字放在数组的后面。我无法创建临时数组,因为它给了我空指针异常。

public static int[] noDups(int[] myArray) {
    int j = 0;
    for (int i = 1; i < myArray.length; i++) {
        if (myArray[i] != myArray[j]) {
            j++;
            myArray[j] = myArray[i];
        }
    }
    return myArray;
}

【问题讨论】:

  • 你不能convin这两个操作,排序和删除重复项?我认为这是更好的解决方案。
  • @astinx - 好吧,他正在对数组进行预排序,因此不需要组合操作。请注意,大多数“好”排序被认为在 O(n log n) 时间内运行,这超过了 O(n) 时间,因此无论如何这对他没有帮助。请注意,虽然组合的搜索/删除操作可能会更快,但这样做会干扰 可组合性,即从较小的函数中生成较大函数的能力(即,正常的过程是有一个sort 函数和 remove-sorted-duplicates 函数,并将它们结合起来)。
  • 你能看一下我的回答吗?我编辑了 t 将解决您的问题。另外,请尝试对答案发表评论并提供反馈。

标签: java arrays sorting duplicates


【解决方案1】:

由于这似乎是家庭作业,我不想给你确切的代码,但这里是做什么:

  • 先遍历数组,看看有多少重复项
  • 创建一个新的大小数组(oldSize - 重复)
  • 再次遍历数组以将唯一值放入新数组中

由于数组已排序,您只需检查 array[n] == array[n+1]。如果不是,那么它不是重复的。检查 n+1 时请注意数组边界。

编辑:因为这涉及到两次运行,它将在 O(2n) -> O(n) 时间内运行。

【讨论】:

  • 非常感谢,我发现这条评论最有帮助。我真的需要帮助理解作业,而不仅仅是代码本身。
  • @MaxFrazier 没问题,有时就是这样。如果它回答了您的问题,请将我的回答标记为已接受。 :)
【解决方案2】:

经过测试并且可以工作(假设数组已经排序)

public static int[] noDups(int[] myArray) { 

    int dups = 0; // represents number of duplicate numbers

    for (int i = 1; i < myArray.length; i++) 
    {
        // if number in array after current number in array is the same
        if (myArray[i] == myArray[i - 1])
            dups++; // add one to number of duplicates
    }

    // create return array (with no duplicates) 
    // and subtract the number of duplicates from the original size (no NPEs)
    int[] returnArray = new int[myArray.length - dups];

    returnArray[0] = myArray[0]; // set the first positions equal to each other
                                 // because it's not iterated over in the loop

    int count = 1; // element count for the return array

    for (int i = 1; i < myArray.length; i++)
    {
        // if current number in original array is not the same as the one before
        if (myArray[i] != myArray[i-1]) 
        {
           returnArray[count] = myArray[i]; // add the number to the return array
           count++; // continue to next element in the return array
        }
    }

    return returnArray; // return the ordered, unique array
}

我的previous answer 使用Integer List 解决这个问题。

【讨论】:

  • 他说没有列表、向量或哈希。
  • @astinx The method has to be in O(n) time, can't use vectors or hashes.
【解决方案3】:

不创建新数组肯定会导致整个初始数组为空。因此,创建一个新数组来存储初始数组中的唯一值。

如何检查唯一值?这是伪代码

uniq = null
loop(1..arraysize)      
  if (array[current] == uniq)  skip
  else  store array[current] in next free index of new array; uniq = array[current]
end loop

正如其他人提到的,通过数组的初始扫描获得数组大小

uniq = null
count = 0
loop(1..arraysize)      
  if (array[current] == uniq)  skip
  else  uniq = array[current] and count++
end loop
create new array of size count

【讨论】:

    【解决方案4】:
    public static int[] findDups(int[] myArray) {
        int numOfDups = 0;
        for (int i = 0; i < myArray.length-1; i++) {
            if (myArray[i] == myArray[i+1]) {
                numOfDups++;
            }
        }
        int[] noDupArray = new int[myArray.length-numOfDups];
        int last = 0;
        int x = 0;
        for (int i = 0; i < myArray.length; i++) {
            if(last!=myArray[i]) {
                last = myArray[i];
                noDupArray[x++] = last;
            }
        }
        return noDupArray;
    }
    

    【讨论】:

      【解决方案5】:
      public int[] noDups(int[] arr){
      
          int j = 0;
          // copy the items without the dups to res
          int[] res = new int[arr.length];
          for(int i=0; i<arr.length-2; i++){
              if(arr[i] != arr[i+1]){
                  res[j] = arr[i];
                  j++;
              }
          }
          // copy the last element
          res[j]=arr[arr.length-1];
          j++;
          // now move the result into a compact array (exact size)
          int[] ans = new int[j];
          for(int i=0; i<j; i++){
              ans[i] = res[i];
          }
          return ans;
      }
      

      第一个循环是 O(n),第二个循环也是如此 - 根据要求,总和为 O(n)。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-02-25
        • 2019-08-11
        • 1970-01-01
        • 2016-01-24
        • 2017-02-14
        • 2012-03-10
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多