【问题标题】:Java - Counting numbers in arrayJava - 计算数组中的数字
【发布时间】:2013-10-31 11:37:49
【问题描述】:

我编写了一个存储一些值的 java prog:

public class array05 {
    public static void main(String[] args) {

        //placement of value
        int arryNum[] = {2,3,4,5,4,4,3};

        //placement of index, to start at 0
        for(int counter=0;counter<arryNum.length;counter++){
            System.out.println(counter + ":" + arryNum[counter]);
        }
    }   
}

生成这样的输出:
0:2
1:3
2:4
3:5
4:4
5:4
6:3

现在我需要计算这个输出#1 中的数字。 输出 #2 应该是这样的:

1:0
2:1
3:2
4:3
5:1

意思是一2,二三,三四,一五。

我不确定如何编写输出 2 的代码。 这里需要二分查找吗?

有人能解释一下吗?

【问题讨论】:

  • 问题陈述是否包括对数组中数字的限制?即,它们是否都保证小于 10?
  • 您正在尝试实现计数排序。
  • @ErnestFriedman-Hill 您好,仅计算我的输出#1 中出现的数字。

标签: java


【解决方案1】:

如果您期望数组中的值介于 1-5 之间(我从您的预期输出中假设)

int arryNum[] = { 2, 3, 4, 5, 4, 4, 3 };
int[] counter = new int[] { 0, 0, 0, 0, 0 };
for (int i = 0; i < arryNum.length; i++) {
    counter[arryNum[i] - 1]++;
}

for (int i = 0; i < counter.length; i++)
    System.out.println((i + 1) + ":" + counter[i]);

【讨论】:

  • 感谢您的帮助,我可以通过这种方法轻松理解!但是我不明白这部分 [arryNum[i] - 1],您介意解释一下吗?
  • 这很容易理解,但如果数组包含的值不在 1 到 5 之间,那么它就会中断。例如这个数组:{ 0, 2, 3, 4, 5, 4, 4, 3 }。由于这些数字似乎不能代表任何只能介于 1-5 之间的数字,因此这不是一个好的做法。 (可能适合做家庭作业)
  • @rzrz 数组中的索引从 0 开始,而你的数字从 1 开始
  • @BenBarkay 你是对的,我说过,这不是通用解决方案,它只适用于给定范围内的条目
【解决方案2】:

我建议你使用Map:

  • 如果其中不存在数字,则将其添加为 value 1。
  • 如果数字存在,则将其值加 1。

然后将地图打印为keyvalue

例如,对于您的数组{2,3,4,5,4,4,3},它将按如下方式工作:

地图是否包含密钥2?不,用值 1 添加它。(345 相同)
地图是否包含4?是的!将其值加 1。现在 key 4 的 value 为 2。
...

【讨论】:

  • 现在没有时间学习地图了!非常有用,可以忽略,也是解决这个问题的最简单方法!
  • 仅供参考:如果实现假定所有映射值(不是键)不能为空,而不是检查键是否存在,只需尝试使用键获取值。如果它返回 null,则您知道该键也不存在。这比遍历键要快得多(当您说“containsKey”时会发生这种情况)。这是 O(1) 与 O(n)。
【解决方案3】:
If you don't want to use Map, this is how you would do it with Arrays only(if you have numbers from 1 to 9 only)

Integer[] countArray = new Integer[10]

// Firstly Initialize all elements of countArray to zero
// Then
for(i=0;i<arryNum.length();i++){

int j = arryNum[i];
countArray[j]++;

}

这个countArray在第一个位置有0的数量,在第二个位置有1的数量等等

【讨论】:

    【解决方案4】:

    这是解决这个问题的方法:

    import java.util.Arrays;
    
    public class array05 {
        public static void main(String[] args) {
            //placement of value
            int arryNum[] = {2,3,4,5,4,4,3};
    
            // Sort the array so counting same objects is easy
            Arrays.sort(arryNum);
    
            int index = 0;  // The current index
            int curnum;     // The current number
            int count;      // The count of this number
            while (index < arryNum.length) {
                // Obtain the current number
                curnum = arryNum[index];
    
                // Reset the counter
                count = 0;
    
                // "while the index is smaller than the amount of items
                // and the current number is equal to the number in the current index,
                // increase the index position and the counter by 1"
                for (; index < arryNum.length && curnum == arryNum[index]; index ++, count++);
    
                // count should contain the appropriate amount of the current
                // number now
                System.out.println(curnum + ":" + count);
            }
        }   
    }
    

    人们使用 Map 发布了很好的解决方案,所以我想我会提供一个始终有效的好解决方案(不仅适用于当前值),而无需使用 Map

    【讨论】:

    • 嗨,感谢您的帮助,但如果我的数组中没有 ONE,如何显示它?例如 - 1:0
    • 您的陈述:“这意味着它计数一个 2、两个 3、三个 4,并且只有一个 5。”让我想到它只需要计算数组中存在的项目。如果这不符合您的需求,我很抱歉 :)
    • 这不是 O(n) 复杂度,但至少是 O(n log(n))
    • 不用担心,您的代码和详细评论向我展示了解决此问题的另一种方法!感谢您的宝贵时间
    • @user902383 我错了Arrays.sort 复杂性:) 谢谢你告诉我。
    【解决方案5】:

    类似这样的:

    //numbers to count
    int arryNum[] = {2,3,4,5,4,4,3};
    
    //map to store results in
    Map<Integer, Integer> counts = new HashMap<Integer, Integer>();
    
    //Do the counting
    for (int i : arryNum) {
       if (counts.containsKey(i) {
          counts.put(i, counts.get(i)+1);
       } else {
          counts.put(i, 1);
       }
    }
    
    //Output the results
    for (int i : counts.keySet()) {
       System.out.println(i+":"+counts.get(i));
    }
    

    【讨论】:

    • 没有人发现故意的错误 - 我有 hasKey() 而不是 containsKey()。现已更正。 :)
    【解决方案6】:

    使用 Map 存储计数值:

    import java.util.HashMap;
    import java.util.Map;
    
    class array05{
      public static void main(String[] args){
          // Container for count values
          Map <Integer, Integer> result = new HashMap<Integer, Integer>();
          int arryNum[] = {2,3,4,5,4,4,3};
          for(int i: arryNum){ //foreach more correct in this case
                if (result.containsKey(i)) result.put(i, result.get(i)+1);
                else result.put(i, 1);
            }
            for (int i: result.keySet()) System.out.println(i + ":" + result.get(i));
      }
    }
    

    结果如下:

    2:1
    3:2
    4:3
    5:1
    

    【讨论】:

    • 谢谢你的地图建议,如果我想包含数组中没有的数字呢?例如:没有第一,因此输出为 1:0
    • 有可能,但更复杂。在这种情况下,您不能使用泛型。可能是您需要使用getClass (docs.oracle.com/javase/7/docs/api/java/lang/Object.html) 从Object 进行转换
    【解决方案7】:

    一种方法是使用地图。当您读取每个数字上的第一个数组时,检查它是否存在于地图中,如果存在,则只需增加分配给数字(键)的值,如果不存在,则在地图中创建一个值为“1”的新键。

    查看http://docs.oracle.com/javase/7/docs/api/java/util/HashMap.html

    【讨论】:

      【解决方案8】:

      你也可以试试这个方法

       int arrayNum[] = {2,3,4,5,4,4,3};
          Map<Integer,Integer> valMap=new HashMap<>();
          for(int i:arrayNum){ // jdk version should >1.7
              Integer val=valMap.get(i);
              if(val==null){
                  val=0;
              }
              valMap.put(i,val+1);
          }
          Arrays.sort(arrayNum);
          for(int i=0;i< arrayNum[arrayNum.length-1];i++){
              System.out.println(i+1+" : "+((valMap.get(i+1)==null) ? 0:valMap.get(i+1)));
          }
      

      输出

          1 : 0
          2 : 1
          3 : 2
          4 : 3
          5 : 1
      

      但以下方式更好

          int arrayNum[] = {2,3,4,5,4,4,3};
          Arrays.sort(arrayNum);
          int countArray[]=new int[arrayNum[arrayNum.length-1]+1];
          for(int i:arrayNum){
             countArray[i]= countArray[i]+1;
          }
          for(int i=1;i<countArray.length;i++){
              System.out.println(i+" : "+countArray[i]);
          }
      

      输出

         1 : 0
         2 : 1
         3 : 2
         4 : 3
         5 : 1
      

      【讨论】:

        【解决方案9】:

        我更喜欢这样的通用解决方案:

        public static <T> Map<T, Integer> toCountMap(List<T> itemsToCount) {
            Map<T, Integer> countMap = new HashMap<>();
        
            for (T item : itemsToCount) {
                countMap.putIfAbsent(item, 0);
                countMap.put(item, countMap.get(item) + 1);
            }
        
            return countMap;
        }
        

        【讨论】:

          【解决方案10】:
          //Count the times of numbers present in an array
          private HashMap<Integer, Integer> countNumbersInArray(int[] array) {
              HashMap<Integer, Integer> hashMap = new HashMap<>();
              for (int item : array) {
                  if (hashMap.containsKey(item)) {
                      hashMap.put(item, hashMap.get(item) + 1);
                  } else {
                      hashMap.put(item, 1);
                  }
              }
              return hashMap;
          }
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 2015-02-18
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2015-01-25
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多