I have been working on a Scrabble assignment. I need to read words from a list, then read each char and assign a value, eventually assigning a total score to each word. That has been done! Phew. Now I need to use the Comparator to sort the words from greatest score to least. I have done a lot of reading and I'm still confused. I know that I could use the interface, but there's also using Comparator with a lambda expression, which is the direction that I think I want to go. I'm just not sure how. I need to compare the sumValue I have for each word, then print the words in decreasing order.
I created 2 loops to read the word (i), then the chars (j). I have printed to the screen the score of each word (sumValue) and its location (i) in my ArrayList. Now I need to use Comparator to compare the scores, and then reorder the location. I think my problem is that I feel like I'm not sorting the Arraylist. I'm sorting the scores, which are not in an ArrayList. Do I need to create a new ArrayList with scores attached to each word and sort that?
CodePudding user response:
You can do it like so. The List
interface has a sort method that takes a
Comparator.
Once such defined Comparator
is Comparator.comparing(Function<? super T,?
extends U>
keyExtractor).
In this case, the KeyExtractor
would be the Word.getValue
method
specified as a method reference (a lambda would also work).
But first you should create a record or class to hold the word and value. That is so when you sort the record based on the value, the word and value will still be together as a unit.
record Word(String getWord, int getValue) {
@Override
public String toString() {
return "%s -> %d".formatted(getWord, getValue);
}
}
Here I have created a list of Word
records. The values are arbitrary for demonstration.
List<Word> list = new ArrayList<>(
List.of(new Word("the", 30), new Word("Hello", 20), new Word("GoodBye", 2)));
list.sort(Comparator.comparing(Word::getValue));
System.out.println(list);
prints
[GoodBye -> 2, Hello -> 20, the -> 30]
You can also sort in reverse order.
list.sort(Comparator.comparing(Word::getValue).reversed());
System.out.println(list);
prints
[GoodBye -> 2, Hello -> 20, the -> 30]
I would also suggest use a Map to hold the letters and their point value.
Map<CString, Integer> letterMap = Map.of("A",1,"B",1,"C",1, ....);
Then you can access them like this.
int point = letterMap.get("A");
CodePudding user response:
I am taking an example of ordering the list according to the length of the word. Here the comparator would be length of the string. The below code is in JavaScript but the logic will be similar.
This link might also help if you are looking for a Java solution Java Comparator class to sort arrays
const arr = ["first", "second", "third", "fourth"];
const out = arr
.map((item) => ({
word: item,
len: item.length
}))
.sort((a, b) => a.len < b.len ? -1 : 1)
.map(item => item.word)
console.log(out)