Печать экземпляров hashmap, упорядоченных по приоритетной очереди - PullRequest
0 голосов
/ 12 мая 2019

Я вставил отдельные слова в текстовый файл и сколько раз они повторяются в хэш-карте как ключи и значения соответственно. Дело в том, что я хочу напечатать k наиболее часто используемых слов в порядке убывания, используя PQ, но, хотя кажется, что легко вставить значения в приоритетную очередь целых чисел, а затем получить k max целых чисел, я не могу понять способ вернуть ключ, соответствующий каждому значению, чтобы снова напечатать его (значения могут быть не уникальными). Решением было бы инвертировать хэш-карту, но это не кажется «безопасным» выбором.

public static void main(int k)throws IOException{

   //Create input stream & scanner
   FileInputStream file = new FileInputStream("readwords.txt");
   Scanner fileInput = new Scanner(file);

   Map<String, Integer> frequency = new HashMap<>();
   LinkedList<String> distinctWords = new LinkedList<String>();
   PriorityQueue<Integer> pQueue = new PriorityQueue<Integer>();

   //Read through file and find the words
   while(fileInput.hasNext()){
       //Get the next word
       String nextWord = fileInput.next().toLowerCase();
       //Determine if the word is in the HashMap
       if(frequency.containsKey(nextWord)) {
           frequency.put(nextWord, frequency.get(nextWord) + 1);
       }
       else {
            frequency.put(nextWord, 1);
            distinctWords.add(nextWord);
       }


    }

    //Close
    fileInput.close();
    file.close();



}

1 Ответ

1 голос
/ 12 мая 2019

Там может быть несколько решений, вот мое. создать class с двумя полями; один для String и один для Integer. Заставьте класс реализовать Comparable и переопределить метод compareTo, чтобы он сравнивал Integers.

public class WordFrequency implements Comparable<WordFrequency> {
    private String word;
    private Integer frequency;

    public WordFrequency(String word, Integer frequency) {
        this.word = word;
        this.frequency = frequency;
    }

    // descending order
    @Override
    public int compareTo(WordFrequency o) {
        return o.getFrequency() - this.getFrequency();
    }

    public Integer getFrequency() {
        return this.frequency;
    }

    @Override
    public String toString() {
        return word + ": " + frequency;
    }
}

Затем конвертируйте map<String, Integer> в PriorityQueue<WordFrequency>:

PriorityQueue<WordFrequency> pQueue = frequency.entrySet().stream()
        .map(m -> new WordFrequency(m.getKey(), m.getValue()))
        .collect(Collectors.toCollection(PriorityQueue::new));

Если вы хотите распечатать его, вы должны использовать poll(), в противном случае порядок не гарантируется.

while(!pQueue.isEmpty())
        System.out.println(pQueue.poll());
...