Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

A subset of a sortedset in Groovy (or Java)

Tags:

java

groovy

Have a SortedSet where I need a specific slice of records based on a specific element in the list.

Example: In the code below, challengeDTO.members is a SortedSet (TreeSet implementation)

I know the location of one member

def memberRank = challengeDTO.members.findIndexOf { it.member.id == membership?.id} + 1

If the memberRank is 66, I want to get a slice of members 60 through 70 ranks.

challengeDTO.members[60..69] won't work because it's a set

Ideas? Suggestions?

Member implementation:

class ChallengeMemberDTO implements Comparable<ChallengeMemberDTO> {

  ChallengeMember member
  Integer total
  String name
  String teamName

  int compareTo(ChallengeMemberDTO t) {
    if (total == t.total) {  // the sortedset will remove duplicates based on same total, which is not desireable
      return name.compareTo(t.name)
    }
    else {
      return t.total.compareTo(total)
    }
  }
}
like image 473
Todd M Avatar asked Dec 07 '25 09:12

Todd M


2 Answers

Try:

(challengeDTO.members as List)[60..69]

Under the covers the Groovy as List type conversion creates an instance of ArrayList and calls addAll, passing your SortedSet. As per the java.util.List JavaDoc addAll "appends all of the elements in the specified collection to the end of this list, in the order that they are returned by the specified collection's iterator". In the java.util.SortedSet JavaDoc it states that "the set's iterator will traverse the set in ascending element order."

So the order of the list will match the order of the SortedSet.

If you're interested, you can take a look at the method in the Groovy source code:

org.codehaus.groovy.runtime.DefaultGroovyMethods.asList(Collection<T> self)

EDIT:

For the sake completeness, in Java you could do the following. It's just what the Groovy code above does under the covers:

SortedSet<ChallendMemberDTO> memberSet = challengeDTO.getMembers();
List<ChallengeMemberDTO> membersPage = new ArrayList<ChallengeMemberDTO>(memberSet).subList(60, 70);
like image 146
Martin Dow Avatar answered Dec 09 '25 22:12

Martin Dow


Well, for that, you have to understand how SortedSet works.

Items that can be used in methods of SortedSet are all those for which the compare() method of the Comparator or the compareTo() method of the items will return a numeric value.

As a consequence, if the compareTo() implementation of your member class allows you to compare members to a number, you can use simply

challengeDTO.members.subSet(60, 70)
like image 27
Riduidel Avatar answered Dec 09 '25 22:12

Riduidel