web-dev-qa-db-fra.com

Comment compter la fréquence des caractères dans une chaîne?

J'ai besoin d'écrire une sorte de boucle pouvant compter la fréquence de chaque lettre d'une chaîne. 
Par exemple: "aasjjikkk" compterait 2 'a', 1 's', 2 'j', 1 'i', 3 'k'. En fin de compte, id comme ceux-ci pour se retrouver dans une carte avec le caractère comme clé et le compte comme valeur. Une bonne idée comment faire cela? 

23
Bill

Vous pouvez utiliser une carte Java et mapper une char à une int. Vous pouvez ensuite parcourir les caractères de la chaîne et vérifier s'ils ont été ajoutés à la carte. Si oui, vous pouvez incrémenter sa valeur.

Par exemple:

HashMap<Character, Integer> map = new HashMap<Character, Integer>();
String s = "aasjjikkk";
for (int i = 0; i < s.length(); i++) {
    char c = s.charAt(i);
    Integer val = map.get(c);
    if (val != null) {
        map.put(c, new Integer(val + 1));
    }
    else {
       map.put(c, 1);
   }
}

À la fin, vous aurez un compte de tous les caractères rencontrés et vous pourrez en extraire leurs fréquences.

Vous pouvez également utiliser la solution de Bozho consistant à utiliser un multiset et à compter le nombre total d’occurrences.

29
xunil154

Vous pouvez utiliser un Multiset (from goyave ). Il vous donnera le compte pour chaque objet. Par exemple:

Multiset<Character> chars = HashMultiset.create();
for (int i = 0; i < string.length(); i++) {
    chars.add(string.charAt(i));
}

Ensuite, pour chaque personnage, vous pouvez appeler chars.count('a') et il renvoie le nombre d'occurrences.

15
Bozho

Une manière concise de faire ceci est:

Map<Character,Integer> frequencies = new HashMap<>();
for (char ch : input.toCharArray()) 
   frequencies.put(ch, frequencies.getOrDefault(ch, 0) + 1);

Nous utilisons un for-each pour parcourir tous les personnages. La frequencies.getOrDefault() obtient une valeur si la clé est présente ou renvoie (par défaut) son deuxième argument. 

7
Sreekanth

Voici une autre solution, même si elle est douteuse.

public char getNumChar(String s) {
    char[] c = s.toCharArray();
    String alphabet = "abcdefghijklmnopqrstuvwxyz";
    int[] countArray = new int[26];
    for (char x : c) {
        for (int i = 0; i < alphabet.length(); i++) {
            if (alphabet.charAt(i) == x) {
                countArray[i]++;
            }
        }
    }

    Java.util.HashMap<Integer, Character> countList = new Java.util.HashMap<Integer, Character>();

    for (int i = 0; i < 26; i++) {
        countList.put(countArray[i], alphabet.charAt(i));
    }
    Java.util.Arrays.sort(countArray);
    int max = countArray[25];
    return countList.get(max);
}
5
Michael

Voici une solution:

Définissez votre propre Pair:

public class Pair
{
    private char letter;
    private int count;
    public Pair(char letter, int count)
    {
        this.letter = letter;
        this.count= count;
    }
    public char getLetter(){return key;}
    public int getCount(){return count;}
}

Ensuite, vous pourriez faire:

public static Pair countCharFreq(String s)
{
    String temp = s;
    Java.util.List<Pair> list = new Java.util.ArrayList<Pair>();
    while(temp.length() != 0)
    {
        list.add(new Pair(temp.charAt(0), countOccurrences(temp, temp.charAt(0))));
        temp.replaceAll("[" + temp.charAt(0) +"]","");
    }
}

public static int countOccurrences(String s, char c)
{
    int count = 0;
    for(int i = 0; i < s.length(); i++)
    {
        if(s.charAt(i) == c) count++;
    }
    return count;
}
2
Eng.Fouad

Utilisation de l'API de flux à partir de JDK-8:

Map<Character, Long> frequency =
            str.chars()
               .mapToObj(c -> (char)c)
               .collect(Collectors.groupingBy(Function.identity(), Collectors.counting()));

ou si vous voulez que les clés soient des entiers:

Map<Character, Integer> frequency =
            str.chars()
               .mapToObj(c -> (char)c)
               .collect(Collectors.groupingBy(Function.identity(), Collectors.summingInt(c -> 1)));

Une autre variante:

Map<Character, Integer> frequency = 
            str.chars()
               .mapToObj(c -> (char)c)
               .collect(Collectors.toMap(Function.identity(), c -> 1, Math::addExact));
2
Aomine

Puisqu'il n'y avait pas de solution Java 8, j'ai pensé à en afficher une. En outre, cette solution est beaucoup plus nette, lisible et concise que certaines des solutions mentionnées ici.

String string = "aasjjikkk";

Map<Character, Long> characterFrequency = string.chars()  // creates an IntStream
    .mapToObj(c -> (char) c) // converts the IntStream to Stream<Character>
    .collect(Collectors.groupingBy(c -> c, Collectors.counting())); // creates a
                                                                    // Map<Character, Long> 
                                                                    // where the Long is
                                                                    // the frequency

Vous pouvez utiliser une CharAdapter et une CharBag de Eclipse Collections et éviter la boxe à Character et Integer.

CharBag bag = CharAdapter.adapt("aasjjikkk").toBag();

Assert.assertEquals(2, bag.occurrencesOf('a'));
Assert.assertEquals(1, bag.occurrencesOf('s'));
Assert.assertEquals(2, bag.occurrencesOf('j'));
Assert.assertEquals(1, bag.occurrencesOf('i'));
Assert.assertEquals(3, bag.occurrencesOf('k'));

Remarque: je suis un partisan des collections Eclipse.

1
Donald Raab

Si cela n'a pas besoin d'être ultra-rapide, créez simplement un tableau d'entiers, un entier pour chaque lettre (seulement des nombres alphabétiques, donc 2 * 26 entiers? Ou des données binaires possibles?). parcourez la chaîne, un caractère à la fois, obtenez l’index de l’entier responsable (par exemple, si vous n’avez que des caractères alphabétiques, vous pouvez avoir «A» à l’indice 0 et obtenir cet index en soustrayant les «A» à «Z» par 'A' juste à titre d'exemple de la façon dont vous pouvez obtenir des index raisonnablement rapides) et incrémenter la valeur dans cet index.

Il existe différentes micro-optimisations pour rendre cela plus rapide (si nécessaire).

0
Bernd Elkemann
NOTE, this will also count the frequencies of empty spaces


import Java.util.HashMap;
import Java.util.Iterator;
import Java.util.Map;
import Java.util.Map.Entry;
import Java.util.Scanner;


public class FrequenceyOfCharacters {

    public static void main(String[] args) {
        System.out.println("Please enter the string to count each character frequencey: ");
        Scanner sc=new  Scanner(System.in);
        String input=sc.nextLine();
        frequenceyCount(input);


    }

    private static void frequenceyCount(String input) {

        Map<Character,Integer> hashCount=new HashMap<>();
        Character c;
        for(int i=0; i<input.length();i++)
        {
           c =input.charAt(i);
           if(hashCount.get(c)!=null){
               hashCount.put(c, hashCount.get(c)+1);
           }else{
               hashCount.put(c, 1);
           }
        }
        Iterator it = hashCount.entrySet().iterator();
        System.out.println("char : frequency");
        while (it.hasNext()) {
            Map.Entry pairs = (Map.Entry)it.next();
            System.out.println(pairs.getKey() + " : " + pairs.getValue());
            it.remove(); 
        }

    }

}
0
weldu
package com.rishi.zava;

import Java.util.HashMap;
import Java.util.Map;
import Java.util.Map.Entry;

public class ZipString {
    public static void main(String arg[]) {
        String input = "aaaajjjgggtttssvvkkllaaiiikk";
        int len = input.length();
        Map<Character, Integer> Zip = new HashMap<Character, Integer>();
        for (int j = 0; len > j; j++) {
            int count = 0;
            for (int i = 0; len > i; i++) {
                if (input.charAt(j) == input.charAt(i)) {
                    count++;
                }
            }
            Zip.put(input.charAt(j), count);
        }
        StringBuffer myValue = new StringBuffer();
        String myMapKeyValue = "";
        for (Entry<Character, Integer> entry : Zip.entrySet()) {
            myMapKeyValue = Character.toString(entry.getKey()).concat(
                    Integer.toString(entry.getValue()));
            myValue.append(myMapKeyValue);
        }
        System.out.println(myValue);
    }
}

Entrée = aaaajjjgggtttssvvkkllaaiiikk

Sortie = a6s2t3v2g3i3j3k4l2

0
RishiKesh Pathak

Question: Prenez la chaîne d'un utilisateur et obtenez la fréquence de chaque caractère. !!!!!!!!!!

import Java.util.HashMap;
import Java.util.Scanner;
public class FrequencyPrograme {
    public static void main(String str[]){
        HashMap<Character,Integer> frequency=new HashMap<Character,Integer>();
        Scanner inputString=new Scanner(System.in);
        System.out.print("Please enter the string.");
        String String  =inputString.next();
        for(int i=0; i<String .length();i++){
            char ch=String .charAt(i);
            Integer value=frequency.get(ch);
            if(value!=null){
                frequency.put(ch, new Integer(value+1));
            }else{
                frequency.put(ch, 1);
            }
        }
        System.out.println(frequency);
    }
}
0
Sanjay Kushwaha

Vous pouvez utiliser une table de hachage avec chaque caractère comme clé et le nombre total devient la valeur.

Hashtable<Character,Integer> table = new Hashtable<Character,Integer>();
String str = "aasjjikkk";
for( c in str ) {
    if( table.get(c) == null )
        table.put(c,1);
    else
        table.put(c,table.get(c) + 1);
}

for( elem in table ) {
    println "elem:" + elem;
}
0
Mike Caputo

Le code possible raccourci en utilisant un HashMap. (Sans ligne énergique enregistre)

private static Map<Character, Integer> findCharacterFrequency(String str) {

        Map<Character, Integer> map = new HashMap<>();

        for (char ch : str.toCharArray()) {
            /* Using getOrDefault(), since Java1.8 */
            map.put(ch, map.getOrDefault(ch, 0) + 1);
        }
        return map;
    }
0
Gaurav Walia
package com.dipu.string;

import Java.util.HashMap;
import Java.util.Map;

public class RepetativeCharInString {
    public static void main(String[] args) {
        String data = "aaabbbcccdddffffrss";
        char[] charArray = data.toCharArray();
        Map<Character, Integer> map = new HashMap<>();
        for (char c : charArray) {
            if (map.containsKey(c)) {
                map.put(c, map.get(c) + 1);
            } else {
                map.put(c, 1);
            }
        }
        System.out.println(map);

    }
}
0
DiptiPrakash
import Java.util.*;
class Charfrequency
{
 public static void main(String a[]){

        Scanner sc=new Scanner(System.in);
        System.out.println("Enter Your String :");
        String s1=sc.nextLine();
        int count,j=1;
        char var='a';
        char ch[]=s1.toCharArray();
        while(j<=26)
        {
           count=0;
                for(int i=0; i<s1.length(); i++)
                {
                    if(ch[i]==var || ch[i]==var-32)
                    {
                        count++;
                    }
                }
                if(count>0){
                System.out.println("Frequency of "+var+" is "+count);
                }
                var++;
                j++;
        }
 }
}
0
Raghu Da
*import Java.util.ArrayList;
import Java.util.Collections;

public class Freq {

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        String temp="zsaaqaaaaaaaabbbbbcc";
    List<String> temp1= new ArrayList<String> ();
    ArrayList<Integer>freq=new ArrayList<Integer>();
    for(int i=0;i<temp.length()-1;i++)
    {       
        temp1.add(Character.toString(temp.charAt(i)));      
    }
    Set<String> uniqset=new HashSet<String>(temp1);
    for(String s:uniqset)
    {
        freq.add(Collections.frequency(temp1, s));
        System.out.println(s+" -->>"+Collections.frequency(temp1, s));
    }
    }

}
           ------Output-------
       a -->>10
       b -->>5
       c -->>1
       q -->>1
       s -->>1
       z -->>1

Utiliser la méthode de la fréquence des collections pour compter la fréquence de char *

0
MinakshiJ

Cela ressemble à la réponse de xunil154, sauf qu'une chaîne est transformée en tableau de caractères et qu'un hashmap lié est utilisé pour conserver l'ordre d'insertion des caractères.

String text = "aasjjikkk";
char[] charArray = text.toCharArray();
Map<Character, Integer> freqList = new LinkedHashMap<Character, Integer>();

        for(char key : charArray) {
            if(freqList.containsKey(key)) {
               freqList.put(key, freqList.get(key) + 1);
            } else
                freqList.put(key, 1);
        }
0
varna

S'il vous plaît essayez le code donné ci-dessous, j'espère qu'il vous sera utile, 

import Java.util.Scanner;

class String55 {
    public static int frequency(String s1,String s2)
    {

        int count=0;
        char ch[]=s1.toCharArray();
        char ch1[]=s2.toCharArray();
        for (int i=0;i<ch.length-1; i++)
        {



                int k=i;

                int j1=i+1;
                int j=0;
                int j11=j;
                int j2=j+1;
                {
                    while(k<ch.length && j11<ch1.length && ch[k]==ch1[j11])
                    {
                    k++;
                    j11++;

                    }


                int l=k+j1;
                int m=j11+j2;
                if( l== m)
                {
                    count=1;
                    count++;
                }





        }
        }
        return count;


    }
    public static void main (String[] args) {
        Scanner sc=new Scanner(System.in);
        System.out.println("enter the pattern");
        String s1=sc.next();
            System.out.println("enter the String");
            String s2=sc.next();
            int res=frequency(s1, s2);
            System.out.println("FREQUENCY==" +res);

    }
}

EXEMPLE DE SORTIE: Entrez le motif Homme Entrez la chaîne Dhimanman FREQUENCY == 2

Merci-bon codage.

0
naveen prasanna