1

For my trading program, a Merchant object has a qualities HashMap of enumerated Qualities with Boolean values.

public class Merchants {
   private Map<Qualities, Boolean> qualities = new HashMap<Qualities, Boolean>();

I would like to give each Merchant object a further ratedQualities HashMap of True Qualities with Byte or Integer values representing the Rating of those Qualities.

For example, a given Merchant could have a "1" Rating associated with their True Stockbroking Quality.

The problem is Java does not let me do this easily. The following code demonstrates my intentions but doesn't compile:

private Map<qualities-TRUE, Byte> ratedQualities = new HashMap<qualities-TRUE, Byte>();

According to this link text one solution is to create a Wrapper for the qualities HashMap. Is this the only solution or is there a better way?

Thanks in advance for your help.

Community
  • 1
  • 1
Arvanem
  • 1,043
  • 12
  • 22
  • 2
    Why do you need the mapping to boolean? Can't you replace that with the Map simply not containing an entry for keys which you would have mapped to false? – Thomas Lötzer Apr 19 '10 at 07:31
  • @Thomas Lotzer, I use the Boolean mapping to determine which Merchants have multiple qualities. Assuming your suggestion is doable, I will try in future to replace that with a Map containing only entries that are true. – Arvanem Apr 19 '10 at 07:35
  • 1
    Following Thomas' comment, if you give up false values, replace the value type to be Integer and then you have both the qualities and their respective rate in a single map. – Eyal Schneider Apr 19 '10 at 07:37
  • @Eyal and Thomas Lotzer, thank you for your suggestions. It makes for simpler code. – Arvanem Apr 19 '10 at 07:41
  • I'm not exactly sure what you want, but I suggest you take a look at the Google Collections framework. It has a Maps class that provides several methods to filter your map based on keys, values, or almost anything else. It also contains a Multimap class you can use to easily map more than one value to a key. – Jorn Apr 19 '10 at 07:53
  • @Thomas Lötzer: DOn't know about the ops case, but adding true or false allows you to use the case without a value to indicate unknown, i.e. a Boolean, if a boolean was acceptable the op could just use a Set as teh value has become redundant. – vickirk Apr 19 '10 at 10:46

3 Answers3

6

Here is an implementation of Merchant using the ideas espoused by Thomas Lötzer and others.

class Merchant
{
    Map<Quality, Integer> ratings = new HashMap<Quality, Integer>();

    boolean hasQuality(Quality quality)
    {
        return ratings.containsKey(quality);
    }

    int getRatingOfQuality(Quality quality)
    {
        Integer rating = ratings.get(quality);
        return (rating != null) ? rating : 0;
    }

    void setRatingOfQuality(Quality quality, int rating)
    {
        ratings.put(quality, rating);
    }
}
Matthew T. Staebler
  • 4,756
  • 19
  • 21
  • Thanks for your help. I have upvoted you, Thomas, Eyal, and Aaron, who all deserve credit for this answer. – Arvanem Apr 19 '10 at 07:53
2

Is there a problem I don't see with just looping over the entries of qualities and adding it to an empty ratedQualities iff the value of the entry in qualities equals true?

That'd be my approach if I understood your question right.

Patrick Bergner
  • 623
  • 8
  • 23
  • Thanks for your answer. You're right that a loop could do this. However I was hoping there was a simple way to initialise this, as I have numerous similar classes to Merchants with numerous similar attributes stored in HashMaps. – Arvanem Apr 19 '10 at 07:39
2

I suggest to replace the Boolean in the map qualities with an Integer and treat Boolean.FALSE as Integer.valueOf(0).

Aaron Digulla
  • 321,842
  • 108
  • 597
  • 820