【问题标题】:Removing duplicates from sorted array list and return size in java without using extra space从排序的数组列表中删除重复项并在java中返回大小而不使用额外的空间
【发布时间】:2018-08-19 09:00:06
【问题描述】:

与下面的代码相比,有没有更好的方法从数组列表中删除重复数据,当遇到更大的输入时,它在 O(n) 中工作。任何建议,将不胜感激。谢谢你。

注意:- 不能使用任何额外的空间,应该就地解决。

输入 :- 它将是一个带有 dups 的排序数组。

代码:-

    public int removeDuplicates(ArrayList<Integer> a) {

        if(a.size()>1){
        for( int i=0;i<a.size()-1;i++ ) {

          if(a.get(i).intValue() == a.get(i+1).intValue() ) {
            a.remove(i);
            i--; 
          }

      }
      }
    return a.size();

    }

请在 coder pad 链接测试代码。

https://coderpad.io/MXNFGTJC

【问题讨论】:

  • 我对java不是很流利,只是一个想法,你有没有想过将arraylist转换为一键设置stackoverflow.com/questions/1429860/…
  • 应该在原地做...不要使用额外的空间
  • [1, 2, 1] 这样的列表会发生什么?问题中的代码将返回 3 并保持列表不变。另外,对于它的价值,我之前做过基准测试,发现使用临时的HashSet 实际上是在 Java 中删除重复项的最快方法。
  • 数组保证有序?

标签: java algorithm data-structures


【解决方案1】:

如果此代码用于删除 未排序 列表的元素,则:

  1. 算法不正确。
  2. 问题与How do I remove repeated elements from ArrayList? 重复(例如...)

如果列表已排序,则:

  1. 算法正确。
  2. 算法不是O(N)。实际上平均是O(ND),其中N 是列表长度,D 是重复数。

    为什么?因为ArrayList::remove(int) 是平均O(N) 操作!

有两种有效的方法可以从列表中删除大量元素:

  1. 创建一个新列表,迭代旧列表并将要保留的元素添加到新列表中。然后要么丢弃旧列表,要么将其清除并将新列表复制到旧列表。

    这对所有标准类型的列表都有效 (O(N))。

  2. 执行滑动窗口移除。带数组的算法是这样的:

        int i = 0;
        for (int j = 0; j < array.length; j++) {
            if (should remove array[j]) {
                // do nothing
            } else {
                array[i++] = array[j];
            }
        }
        // trim array to length i, or assign nulls or something.
    

    如您所见,这执行了一次遍历数组,并且是O(N)。它还避免分配任何临时空间。

    您可以使用ArrayList::get(int)ArrayList::set(int, &lt;E&gt;) 实现滑动窗口移除...然后重复移除最后一个元素以修剪列表。

【讨论】:

  • 不是put,是set
  • 谢谢。修好了。
【解决方案2】:

以下是一些提高性能的想法:

  1. 从 ArrayList 中逐个删除元素可能会很昂贵,因为您必须将所有内容移到该元素之后。除了 ArrayList,您可能会考虑使用允许 O(1) 删除的不同列表实现。或者,如果您必须使用 ArrayList 并且不允许使用任何临时数据结构,则可以通过将使用 set() 而不是 remove() 的递归调用链接在一起来重建数组。

  2. 对于包含数百万个元素的列表,请考虑使用并行处理解决方案来利用多个进程的强大功能。 Java 流是实现此目的的一种简单方法。

【讨论】:

  • 如果需要使用相同的 ArrayList,set() 将是一个很好的解决方案,可以将其保持在 O(n) 中。
【解决方案3】:
List<Integer> l = new ArrayList<Integer>();
//add some elements to l
System.out.println(l.stream().distinct().collect(Collectors.toList()));

【讨论】:

    猜你喜欢
    • 2021-02-25
    • 2011-10-26
    • 2017-12-06
    • 1970-01-01
    • 2013-09-26
    • 2016-10-01
    • 2019-02-18
    • 2021-12-31
    • 2010-11-22
    相关资源
    最近更新 更多