【问题标题】:missing elements from two arrays in javajava中两个数组的元素缺失
【发布时间】:2010-02-05 14:03:15
【问题描述】:

我们如何从两个数组中找出缺失的元素? 例如:

        int []array1 ={1,2,3,4,5};           
        int []array2 ={3,1,2};

从上面的两个数组中我想找出第二个数组中缺少的元素是什么?

【问题讨论】:

  • 如果您已经了解一些编程/计算机科学,我会选择不属于我的答案。如果您只是在学习,请尝试自己编写所有代码,以便您理解它。
  • 在任一数组中是否允许重复值?

标签: java


【解决方案1】:

将它们转换为Sets 并使用removeAll

第一个问题是如何将原始int[] 转换为集合。 使用Guava,您可以使用:

List<Integer> list1 = Ints.asList(array1);
List<Integer> list2 = Ints.asList(array2);

Apache commons(我不熟悉)显然有类似的东西。

现在转换成一个集合:

Set<Integer> set1 = new HashSet<Integer>(list1);

并计算差异:

set1.removeAll(list2);

并将结果转换回数组:

return Ints.toArray(set1);

【讨论】:

  • 这假定两个数组中都不允许有重复项。
【解决方案2】:

如果允许在数组中重复,一个有效的 (O(n)) 解决方案是通过迭代第一个数组来创建频率表 (Map),然后使用映射匹配第二个数组中的任何元素数组。

Map<Integer, Integer> freqMap = new HashMap<Integer, Integer>();

// Iterate over array1 and populate frequency map whereby
// the key is the integer and the value is the number of
// occurences.
for (int val1 : array1) {
  Integer freq = freqMap.get(val1);

  if (freq == null) {
    freqMap.put(val1, 1);
  } else {
    freqMap.put(val1, freq + 1);
  }
}

// Now read the second array, reducing the frequency for any value
// encountered that is also in array1.
for (int val2 : array2) {
  Integer freq = freqMap.get(val2);

  if (freq == null) {
    freqMap.remove(val2);
  } else {
    if (freq == 0) {
      freqMap.remove(val2);   
    } else {
      freqMap.put(freq - 1);
    }
  }
}

// Finally, iterate over map and build results.
List<Integer> result = new LinkedList<Integer>();

for (Map.Entry<Integer, Integer> entry : freqMap.entrySet()) {
  int remaining = entry.getValue();

  for (int i=0; i<remaining; ++i) {
    result.add(entry.getKey());
  }
}

// TODO: Convert to int[] using the util. method of your choosing.

【讨论】:

    【解决方案3】:

    获取不匹配数字的简单逻辑。

    public static int getelements(int[] array1, int[] array2)
    {
        int count = 0;
        ArrayList unMatched = new ArrayList();
        int flag = 0;
        for(int i=0; i<array1.length ; i++)
        {   flag=0;
            for(int j=0; j<array2.length ; j++)
            {
                    if(array1[i] == array2[j]) {
                        flag =1;
                        break;
                    }
    
    
            }
            if(flag==0)
            {
                unMatched.add(array1[i]);
            }
        }
    
            System.out.println(unMatched);
    
        return unMatched.size();
    
    }
    
    public static  void  main(String[] args) {
    // write your code here5
    
        int array1[] = {7,3,7,2,8,3,2,5};
        int array2[] = {7,4,9,5,5,10,4};
    
    
        int count;
        count = getelements(array1,array2);
    
        System.out.println(count);
    
    
    
    }
    

    【讨论】:

    • 请解释你的代码是做什么的以及它是怎么做的。
    • 方法 getelements 需要 2 个数组。现在使用 2 个循环将有助于比较数组 1 的元素和数组 2 的元素。然后,如果条件匹配,我将打破该循环。并将其插入数组列表,因为允许重复。就是这样。
    【解决方案4】:

    您可以使用 Set 及其方法。此操作将是一个固定的差异。

    【讨论】:

      【解决方案5】:

      天真的方法是简单地在一个数组中搜索另一个数组的每个元素(使用 for 循环)。如果您首先对两个数组进行排序,它会变得更加高效。

      【讨论】:

        【解决方案6】:

        考虑使用交集方法:

        一个健康的讨论可以在:

        http://www.coderanch.com/t/35439/Programming-Diversions/Intersection-two-arrays

        【讨论】:

          【解决方案7】:

          您可以创建另外两个 int 数组来存储每个值的多重性。每次找到该值对应的数组的索引递增,然后比较数组。

          这可能不是最“有效”的方式,但它是一个非常简单的概念。

          【讨论】:

            【解决方案8】:

            Guava 库可以提供帮助;您需要更改 Set 中的 Array 才能使用 API。

            【讨论】:

              【解决方案9】:

              @finnw 我相信你在想commons-collections。 需要导入 org.apache.commons.collections.CollectionUtils; 得到析取函数。

              使用 disjunction 方法将找到所有在交集中找不到的对象。

              Integer[] array1 ={1,2,3,4,5};           
              Integer[] array2 ={3,1,2};
              List list1 = Arrays.asList(array1);
              List list2 = Arrays.asList(array2);
              Collection result = CollectionUtils.disjunction(list1, list2);
              System.out.println(result); // displays [4, 5]
              

              【讨论】:

              • 我正在考虑一种将int[] 转换为Integer[]List&lt;Integer&gt; 的方法。我不知道disjunction(我认为它在 Guava 中还没有等价物。)
              • @finnw 我不认为 List 有一个,但是 commons-lang 的 ArrayUtils.toObject(int[] array) 返回 Integer[]。
              【解决方案10】:

              这不是最有效的方法,但它可能是 Java 中最简单的方法:

              public static void main(final String[] args) {
                      final int[] a = { 1, 2, 3, 4, 5 };
                      final int[] b = { 3, 1, 2 };
                      // we have to do this just in case if there might some values that are missing in a and b
                      // example: a = { 1, 2, 3, 4, 5 }; b={ 2, 3, 1, 0, 5 }; missing value=4 and 0
                      findMissingValue(b, a);
                      findMissingValue(a, b);
                  }
              
                  private static void findMissingValue(final int[] x, final int[] y) {
                      // loop through the bigger array
                      for (final int n : x) {
                          // for each value in the a array call another loop method to see if it's in there
                          if (!findValueSmallerArray(n, y)) {
                              System.out.println("missing value: " + n);
                              // break;
                          }
                      }
                  }
              
                  private static boolean findValueSmallerArray(final int n, final int[] y) {
                      for (final int i : y) {
                          if (n == i) {
                              return true;
                          }
                      }
                      return false;
                  }
              

              【讨论】:

                猜你喜欢
                • 2019-05-18
                • 1970-01-01
                • 2019-03-07
                • 2020-08-08
                • 1970-01-01
                • 2011-07-12
                • 2015-07-29
                • 1970-01-01
                相关资源
                最近更新 更多