42

Is there any method for counting the occurrence of each item on an array?

Lets say I have:

String[] array = {"name1","name2","name3","name4", "name5"};

Here the output will be:

name1 1
name2 1
name3 1
name4 1
name5 1

and if I have:

String[] array = {"name1","name1","name2","name2", "name2"};

The output would be:

name1 2
name2 3

The output here is just to demonstrate the expected result.

1
  • Probably not, but it should be simple enough for you to implement a method on your own considering how easy the task is. It will perform in O(n) no matter what I reckon anyway (unless you make some assumptions about sorting to increase this speed) Commented Nov 11, 2011 at 18:59

23 Answers 23

51
List asList = Arrays.asList(array);
Set<String> mySet = new HashSet<String>(asList);

for(String s: mySet){
 System.out.println(s + " " + Collections.frequency(asList,s));
}
Sign up to request clarification or add additional context in comments.

3 Comments

from my experience, Collections.frequency is too slow.Avoid if performance is a concern.
Not really, if it is a HashSet or HashMap.
I think Collectors.groupingBy works better than Collections.frequency
49

With , you can do it like this:

String[] array = {"name1","name2","name3","name4", "name5", "name2"};
Arrays.stream(array)
      .collect(Collectors.groupingBy(s -> s))
      .forEach((k, v) -> System.out.println(k+" "+v.size()));

Output:

name5 1
name4 1
name3 1
name2 2
name1 1

What it does is:

  • Create a Stream<String> from the original array
  • Group each element by identity, resulting in a Map<String, List<String>>
  • For each key value pair, print the key and the size of the list

If you want to get a Map that contains the number of occurences for each word, it can be done doing:

Map<String, Long> map = Arrays.stream(array)
    .collect(Collectors.groupingBy(s -> s, Collectors.counting()));

For more informations:

Hope it helps! :)

1 Comment

I think Collectors.groupingBy works better
18

You could use a MultiSet from Google Collections/Guava or a Bag from Apache Commons.

If you have a collection instead of an array, you can use addAll() to add the entire contents to the above data structure, and then apply the count() method to each value. A SortedMultiSet or SortedBag would give you the items in a defined order.

Google Collections actually has very convenient ways of going from arrays to a SortedMultiset.

2 Comments

The link to Bag is 404.
I used getCardinalityMap() from org.apache.commons.collections.CollectionUtils.
5

Using HashMap it is walk in the park.

main(){
    String[] array ={"a","ab","a","abc","abc","a","ab","ab","a"};
    Map<String,Integer> hm = new HashMap();

    for(String x:array){

        if(!hm.containsKey(x)){
            hm.put(x,1);
        }else{
            hm.put(x, hm.get(x)+1);
        }
    }
    System.out.println(hm);
}

4 Comments

this works, but could explain little about hm.put(x, hm.get(x)+1); part ? thx
I meant how is hm.get(x) actually act like a counter not item value?
@ikel If key (x in this case) is already there in the hm, get the corresponding value, increment by one and store it back.
This works but has poor performance
4

I wrote a solution for this to practice myself. It doesn't seem nearly as awesome as the other answers posted, but I'm going to post it anyway, and then learn how to do this using the other methods as well. Enjoy:

public static Integer[] countItems(String[] arr)
{
    List<Integer> itemCount = new ArrayList<Integer>();
    Integer counter = 0;
    String lastItem = arr[0];

    for(int i = 0; i < arr.length; i++)
    {
        if(arr[i].equals(lastItem))
        {
            counter++;
        }
        else
        {
            itemCount.add(counter);
            counter = 1;
        }
        lastItem = arr[i];
    }
    itemCount.add(counter);

    return itemCount.toArray(new Integer[itemCount.size()]);
}

public static void main(String[] args)
{
    String[] array = {"name1","name1","name2","name2", "name2", "name3",
            "name1","name1","name2","name2", "name2", "name3"};
    Arrays.sort(array);
    Integer[] cArr = countItems(array);
    int num = 0;
    for(int i = 0; i < cArr.length; i++)
    {
        num += cArr[i]-1;
        System.out.println(array[num] + ": " + cArr[i].toString());
    }
}

1 Comment

It won't work for array like this: String[] array = { "Gates", "Michael","Gates","Peterson","Bush","Johnson","Johnson","Gates"};
3

It can be done in a very simple way using collections please find the code below

String[] array = {"name1","name1","name2","name2", "name2"};
List<String> sampleList=(List<String>) Arrays.asList(array);
for(String inpt:array){
int frequency=Collections.frequency(sampleList,inpt);
System.out.println(inpt+" "+frequency);
}

Here the output will be like name1 2 name1 2 name2 3 name2 3 name2 3

To avoid printing redundant keys use HashMap and get your desired output

1 Comment

We can also pass the sampleList above to constructor of TreeSet and then loop to get the result
2

I would use a hashtable with in key takes the element of the array (here string) and in value an Integer.

then go through the list doing something like this :

for(String s:array){
if(hash.containsKey(s)){
  Integer i = hash.get(s);
  i++;
}else{
  hash.put(s, new Interger(1));
}

1 Comment

This doesn't work, you'd have to use hash.put(s, hash.get(s) + 1);. Doing i++; doesn't update the integer inside the hashtable. There's also other typos.
2

You can do it by using Arrays.sort and Recursion. The same wine but in a different bottle....

import java.util.Arrays;

public class ArrayTest {
public static int mainCount=0;

public static void main(String[] args) {
    String prevItem = "";
    String[] array = {"name1","name1","name2","name2", "name2"};
    Arrays.sort(array);

    for(String item:array){
        if(! prevItem.equals(item)){
            mainCount = 0;
            countArray(array, 0, item);
            prevItem = item;
        }
    }
}

private static void countArray(String[] arr, int currentPos, String item) {
    if(currentPos == arr.length){
        System.out.println(item + " " +  mainCount);
        return;
    }
    else{
        if(arr[currentPos].toString().equals(item)){
            mainCount += 1;
        }
        countArray(arr, currentPos+1, item);
    }
  }
}

Comments

2

Count String occurence using hashmap, streams & collections

import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.stream.Collectors;

public class StringOccurence {

public static void main(String args[]) {

    String[] stringArray = { "name1", "name1", "name2", "name2", "name2" };
    countStringOccurence(stringArray);
    countStringOccurenceUsingStream(stringArray);
    countStringOccurenceUsingCollections(stringArray);
}

private static void countStringOccurenceUsingCollections(String[] stringArray) {
    // TODO Auto-generated method stub
    List<String> asList = Arrays.asList(stringArray);
    Set<String> set = new HashSet<String>(asList);
    for (String string : set) {
        System.out.println(string + "   -->   " + Collections.frequency(asList, string));
    }

}

private static void countStringOccurenceUsingStream(String[] stringArray) {
    // TODO Auto-generated method stub
    Arrays.stream(stringArray).collect(Collectors.groupingBy(s -> s))
            .forEach((k, v) -> System.out.println(k + "   -->   " + v.size()));
}

private static void countStringOccurence(String[] stringArray) {
    // TODO Auto-generated method stub
    Map<String, Integer> map = new HashMap<String, Integer>();
    for (String s : stringArray) {
        if (map.containsKey(s)) {
            map.put(s, map.get(s) + 1);
        } else {
            map.put(s, 1);
        }
    }

    for (Map.Entry<String, Integer> entry : map.entrySet()) {
        System.out.println(entry.getKey() + "   -->   " + entry.getValue());
    }

}

}

Comments

1

Here is my solution - The method takes an array of integers(assuming the range between 0 to 100) as input and returns the number of occurrences of each element.

let's say the input is [21,34,43,21,21,21,45,65,65,76,76,76]. So the output would be in a map and it is: {34=1, 21=4, 65=2, 76=3, 43=1, 45=1}

public Map<Integer, Integer> countOccurrence(int[] numbersToProcess) {
    int[] possibleNumbers = new int[100];
    Map<Integer, Integer> result = new HashMap<Integer, Integer>();

    for (int i = 0; i < numbersToProcess.length; ++i) {
      possibleNumbers[numbersToProcess[i]] = possibleNumbers[numbersToProcess[i]] + 1;
      result.put(numbersToProcess[i], possibleNumbers[numbersToProcess[i]]);
    }

    return result;
}

Comments

1

There are several methods which can help, but this is one is using for loop.

import java.util.Arrays;

public class one_dimensional_for {

private static void count(int[] arr) {

    Arrays.sort(arr);

    int sum = 0, counter = 0;

    for (int i = 0; i < arr.length; i++) {
        if (arr[0] == arr[arr.length - 1]) {
            System.out.println(arr[0] + ": " + counter + " times");
            break;
        } else {
            if (i == (arr.length - 1)) {
                sum += arr[arr.length - 1];
                counter++;
                System.out.println((sum / counter) + " : " + counter
                        + " times");
                break;
            } else {
                if (arr[i] == arr[i + 1]) {
                    sum += arr[i];
                    counter++;
                } else if (arr[i] != arr[i + 1]) {
                    sum += arr[i];
                    counter++;
                    System.out.println((sum / counter) + " : " + counter
                            + " times");
                    sum = 0;
                    counter = 0;
                }
            }
        }
    }
}

public static void main(String[] args) {
    int nums[] = { 1, 1, 1, 1, 2, 2, 2, 3, 3, 4, 5, 5, 5, 5, 6 };
    count(nums);
}

}

Comments

0

You can use Hash Map as given in the example below:

import java.util.HashMap;
import java.util.Set;

/**
 * 
 * @author Abdul Rab Khan
 * 
 */
public class CounterExample {
    public static void main(String[] args) {
        String[] array = { "name1", "name1", "name2", "name2", "name2" };
        countStringOccurences(array);
    }

    /**
     * This method process the string array to find the number of occurrences of
     * each string element
     * 
     * @param strArray
     *            array containing string elements
     */
    private static void countStringOccurences(String[] strArray) {
        HashMap<String, Integer> countMap = new HashMap<String, Integer>();
        for (String string : strArray) {
            if (!countMap.containsKey(string)) {
                countMap.put(string, 1);
            } else {
                Integer count = countMap.get(string);
                count = count + 1;
                countMap.put(string, count);
            }
        }
        printCount(countMap);
    }

    /**
     * This method will print the occurrence of each element
     * 
     * @param countMap
     *            map containg string as a key, and its count as the value
     */
    private static void printCount(HashMap<String, Integer> countMap) {
        Set<String> keySet = countMap.keySet();
        for (String string : keySet) {
            System.out.println(string + " : " + countMap.get(string));
        }
    }
}

Comments

0

This is a simple script I used in Python but it can be easily adapted. Nothing fancy though.

def occurance(arr):
  results = []
  for n in arr:
      data = {}
      data["point"] = n
      data["count"] = 0
      for i in range(0, len(arr)):
          if n == arr[i]:
              data["count"] += 1
      results.append(data)
  return results

Comments

0

you can find using HashMap with simple technic

public class HashMapExample {
    public static void main(String[] args) {
        stringArray();          
    }
public static void stringArray()
{
    String[] a = {"name1","name2","name3","name4", "name5"};

    Map<String, String> hm = new HashMap<String, String>();
    for(int i=0;i<a.length;i++)
    {
    String bl=(String)hm.get(a[i]);
    if(bl==null)
    {
        hm.put(a[i],String.valueOf(1));
    }else
    {
        String k=hm.get(a[i]);
        int j=Integer.valueOf(k);
        hm.put(a[i],String.valueOf(j+1));
    }

    }
    //hm.entrySet();
    System.out.println("map elements are "+hm.toString());
}

}

Comments

0

You could use

for (String x : array){
   System.out.println(Collections.frequency(array,x));
}

Comments

0

My favorite method using Map.getOrDefault, which is available since Java 8:

Map<String, Integer> map = new HashMap<>();
for (String s : array) {
  map.put(s, map.getOrDefault(s, 0) + 1);
}

In this code snippet, we iterate over each string in the input array and update the count of that string in the map. If the string is not already present in the map, it is added with a default value of 0 using getOrDefault.

Comments

-1

You can use HashMap, where Key is your string and value - count.

Comments

-1

// An Answer w/o using Hashset or map or Arraylist

public class Count {
    static String names[] = {"name1","name1","name2","name2", "name2"};
    public static void main(String args[]) {

        printCount(names);

    }

    public static void printCount(String[] names){

        java.util.Arrays.sort(names);
        int n = names.length, c;
        for(int i=0;i<n;i++){
            System.out.print(names[i]+" ");
        }
        System.out.println();
        int result[] = new int[n];
        for(int i=0;i<n;i++){
            result[i] = 0;
        }

        for(int i =0;i<n;i++){
            if (i != n-1){
                for(int j=0;j<n;j++){
                    if(names[i] == names[j] )
                        result[i]++;
                }
            }
            else if (names[n-2] == names[n-1]){
            result[i] = result[i-1];
         }

         else result[i] = 1;
        }
        int max = 0,index = 0;
        for(int i=0;i<n;i++){
         System.out.print(result[i]+"     ");
            if (result[i] >= max){
                max = result[i];
                index = i;
            }

        }
    }
}

Comments

-1
public class Main
{
    public static void main(String[] args) {
        
        String[] a ={"name1","name1","name2","name2", "name2"};
        for (int i=0;i<a.length ;i++ )
        {
            int count =0;
            int count1=0;
            for(int j=0;j<a.length;j++)
            {
                if(a[i]==a[j])
                {
                    count++;
                    
                }
            }
            for(int j=i-1;j>=0 ;j--)
            {
                if(a[i]==a[j])
                {
                    count1++;
                }
            }
            if(count1 ==0)
            {
                System.out.println(a[i]+" occurs :"+count);
            }
        }
    }
}

Comments

-1
import java.util.HashMap;
import java.util.Map;

public class FrequencyUsingMap {

    public static void main(String[] args) {
        int a[] = {1,1,1,1,2,2,3,4,1};
        int num = 0;
        int maxfreq = 0;
        int maxnum =0;
        Map<Integer, Integer> map = new HashMap<>();
        for(int i = 0; i<a.length; i++){
            num = a[i];
        
            if(map.containsKey(num)){
                int frq = map.get(num);
                frq++;
                map.put(num, frq);
                if(frq>maxfreq){
                    maxfreq = frq;
                    maxnum = num;
                }
            }else{
                map.put(num, 1);
            }
        }
        System.out.println(map);
        System.out.println("number "+ maxnum + " having max frequency " +maxfreq);
    }
}

1 Comment

Please try to add some description as well with your comment to make it more understandable. Do not only post codes as answers.
-1

I wrote an easy solution for this, have a look:

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

    double [] x = { -4, 3, -9, -5, 4, 1 }; 
    double p = 0;
    double n = 0;
    int z = 0;

    for (int i = 0; i < x.length; i++) {

        if (x[i] > 0) {
            p += 1;

        }
        if (x[i] < 0) {
            n += 1;

        }
        if (x[i] == 0) {
            z += 1;

        }
    }
    double ppi = p / x.length;
    double pni = n / x.length;
    int pzi = z / x.length;

    System.out.println(ppi);
    System.out.println(pni);
    System.out.println(pzi);

}
}

Comments

-1
public class test {

    static String uniq[];
    
    public static String[] convertWordArray(String str) {
        str = str.toLowerCase();
        String test[] = str.split(" ");
        return test;
    }
    
    public static void findRepetitiveWordsinString(String str) {
        String[] test =convertWordArray(str);
        int len = test.length;
        int count;
        List<Integer> l = new ArrayList<>();
        for (int i = 0; i < len; i++) {
            count = 1;
            for (int j = i + 1; j < len; j++) {
                if (test[i].equals(test[j])) {
                    count++;
                    test[j] = "0";
                }
            }
            if (count > 1 && test[i] != "0") {
                System.out.println(test[i]);
                l.add(i);
            }
        }
        System.out.println("Repetitive words at index :" +l);
        uniq = new String[l.size()];    
        for (int i = 0; i < l.size(); i++) {
            uniq[i] = test[l.get(i)];
        }
        System.out.println("Number of words that are repeated: " + uniq.length);
    }

    public static void countMatches(String a[], String b[]) {
        int count;
        for (int i = 0; i < a.length; i++) {
            count = 0;
            for (int j = 0; j < b.length; j++) {
                if (a[i].equals(b[j]))
                    count++;
            }
            if (count > 1) {
                System.out.println("Repeating word is: " + a[i] + "  and the repeating count is " + count);
            }
        }
    }

    public static void main(String[] args) {
        String str;
        Scanner scanner = new Scanner(System.in);
        str = scanner.nextLine();
        findRepetitiveWordsinString(str);
        countMatches(uniq, convertWordArray(str));
    }
}

Comments

-2
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;

public class MultiString {

    public HashMap<String, Integer> countIntem( String[] array ) {

        Arrays.sort(array);
        HashMap<String, Integer> map = new HashMap<String, Integer>();
        Integer count = 0;
        String first = array[0];
        for( int counter = 0; counter < array.length; counter++ ) {
            if(first.hashCode() == array[counter].hashCode()) {
                count = count + 1;
            } else {
                map.put(first, count);
                count = 1;
            }
            first = array[counter];
            map.put(first, count);
        }

        return map;
    }

    /**
     * @param args
     */
    public static void main(String[] args) {
        // TODO Auto-generated method stub
        String[] array = { "name1", "name1", "name2", "name2", "name2",
                "name3", "name1", "name1", "name2", "name2", "name2", "name3" };

        HashMap<String, Integer> countMap = new MultiString().countIntem(array);
        System.out.println(countMap);
    }
}



Gives you O(n) complexity.

1 Comment

You may want to provide some explanation to your code.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.