【问题标题】:Performance when searching for missing numbers in array在数组中搜索缺失数字时的性能
【发布时间】:2011-10-11 13:19:05
【问题描述】:

Given 是一个列表,其中包含 1-20 之间的除 2 个以外的所有数字(随机排序)。 我需要找到那两个数字。

这是我想出的(工作)程序:

public static void main(String[] args) {
    int[] x= {1,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19};
    ArrayList al= new ArrayList();
    Map map= new HashMap();
    for(int i=0;i<x.length;i++)
    {
        map.put(x[i], x[i]);
    }
    for(int i=1;i<=20;i++)
    {
        if(map.get(i)==null)
            al.add(i);
    }
    for(int i=0;i<al.size();i++)
    {
        System.out.println(al.get(i));
    }
}

我想知道从性能角度(内存和bigO(n))这个程序是否好?

【问题讨论】:

    标签: java performance algorithm search arraylist


    【解决方案1】:

    另一种选择是使用 BitSet,其中每个位都设置为数组中的相应数字。

    【讨论】:

      【解决方案2】:

      您不需要地图。只是一个额外的大小为 20 的布尔数组。

      for (int i = 0; i < input.length; i++)
         arr[input[i]] = true;
      
      for (int i = 1; i <= 20; i++)
         if (arr[i] == false) {
            //number `i` is missing
         }     
      

      现在我将公开一个简单的数学解决方案。

      首先对数组中的所有数字求和。例如,5, 1, 4 中的数字来自 1, 2, 3, 4, 5。所以23 不见了。我们可以很容易地用数学找到它们。

      5 + 1 + 4 = 10
      1 + 2 + 3 + 4 + 5 = 15
      

      所以我们知道x + y = 15 - 10 = 5 现在我们将得到第二个等式:

      1 * 4 * 5 = 20
      1 * 2 * 3 * 4 * 5 = 120
      => x * y = 120 / 20 = 6
      

      所以:

      x + y = 5
      x * y = 6
      

      => x = 2, y = 3 or x = 3, y = 2 是一样的。

      所以x = 2, y = 3

      【讨论】:

      • 布尔数组将更容易理解(并节省空间)。
      • @Stephen C - 是的,我写它更像是一个伪代码。我将进行编辑以使其更清晰。
      • 我喜欢使用数学的想法,但我猜你很快就会需要一个很长的 BigInteger,如果列表增加的话,不久之后的产品。
      • @user unknown - 是的,非常正确:)
      【解决方案3】:

      它不应该比线性时间 O(n) 更糟糕:一次运行填充标志数组,第二次运行检查标志数组。

      【讨论】:

        【解决方案4】:

        由于 map.put 操作,您的代码以 O(n) 运行。下面的 for 循环在最坏的情况下也会以 O(n) 运行,所以总的来说,你的整个函数运行在 O(n)。

        您可以进一步优化您的代码。例如,您正在使用额外的内存。为了改进这一点,您需要提出 2 个 eqns 来推断缺失的数字 x 和 y。

        等式1: 求和(1 到 20)= n*(n+1)/2 将数组中的所有数字相加并存储在 temp 中。 x+y = n*(n+1)/2 - 温度

        等式2: 乘(1 到 20)= n! 将数组中的所有数字相乘并存储在 temp 中。 x*y = 温度 / n!

        求解方程得到 x 和 y。

        所以这将在没有太多内存的情况下运行 O(n)。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 1970-01-01
          • 2018-04-14
          • 2019-09-03
          • 2013-07-05
          • 2014-08-22
          • 2014-08-02
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多