What is the best way to model priority/preferences in a domain?
E.g. assume I have a class Person
representing a person and has some preferences e.g. PersonX
likes pizza, spaggetti and omelete and actually he would prefer spagetti over pizza.
How are these best modelled?
The first thought would be just to put them in a List
(as member variable of Person
) keeping the preference according to insertion order e.g. the first in the list is the most prefered, then the second in the list the second most prefered etc but this seems to me to end up being too tedious. E.g. when I want to do searches or associations for preferences etc.
Perhaps there is a standard approach for problems like this?

- 52,998
- 69
- 209
- 339
4 Answers
You could use the list as you proposed and add a method to your Person class that would return a Comparator<Preference>
which would be able to compare 2 preferences for that person:
Person somebody.addPreference(pizzaPreference);
Person somebody.addPreference(omelettePreference);
....
Comparator<Preference> c = somebody.getPreferenceComparator();
boolean prefersPizzaOverOmelette = (c.compare(pizzaPreference, omelettePreference) > 0);
boolean hasNoPreferenceBetweenPizzaAndOmelette = (c.compare(pizzaPreference, omelettePreference) == 0);
And the comparator would simply check the index of the preference in your list (if it contains that preference etc.).

- 321,522
- 82
- 660
- 783
You could use a priority queue for representing object priorities, and define an appropriate Comparator
for your class that takes into account the rules described. The queue uses a priority heap that will take care of maintaining the objects sorted by priority as they're being inserted.

- 232,561
- 37
- 312
- 386
-
You mean each `Person` has an associated `PriorityQueue`? Also what if I need the 2nd preference instead of the `max` preference for some reason in some part of the flow? – Cratylus May 01 '12 at 15:18
-
No, put all of the persons in _one_ priority queue, the ordering of the queue will be the ordering of their priorities. If you need the second-highest, then pop two persons from the queue. It's all about the way [heaps](http://en.wikipedia.org/wiki/Heap_(data_structure)) work, take a look at the link. – Óscar López May 01 '12 at 17:10
-
What do you mean `put all of the persons in one priority queue`? Is this the `priority queue` for `pizza` for example? Does this PQ belong to an object? – Cratylus May 01 '12 at 19:06
-
A PQ is just another collection (like ArrayList, LinkedList, etc.) Of course, it should belong into an object. Read this [post](http://stackoverflow.com/a/683049/201359). – Óscar López May 01 '12 at 21:18
-
I am not sure how you suggest to use a PQ here. 1 PQ for e.g pizzas? 1 PQ for persons? What model you suggest? – Cratylus May 01 '12 at 21:28
Use a class structure like this...(pardon the sloppy Java...I'm a C# guy)
public class PersonPreference
{
public Preference preference;
public int rank;
}
Then, allow your users to sort their preferences (hence, the rank column), and order on that property/column when necessary.
EDIT
Looking at this again, I want to redefine my class. A preference should be a user's like in comparison to another like...
public class PersonLike
{
public string like;
public int rank;
}
This new class defines something a person likes, and it allows for a rank so that when you have many instances of this class (or a data representation of it), they can be ranked, which in affect, creates the preference, because a preference is essentially a user liking something over something else. A like by itself is not a preference because it is not being compared against anything else.
This approach allows for n interests to be ranked against each other creating a large collection of preferences.

- 6,841
- 8
- 39
- 53
-
`allow your users to sort their preferences ..` this is more or less what I am asking about. Also what is a `Preference`? – Cratylus May 01 '12 at 15:21
-
Preference can be anything....but looking at your question again, I think making this a free form string would be better. That way they could type in "Pizza" or "Spaghetti", etc...., – ctorx May 01 '12 at 19:34
-
Preference
as a whole is a complete Entity in its own, though would not have any meaning unless it is associated with any Person
but can live on its own.
As far as Preference priority is concerned, Preference
doesn't have any priority Omelet, Pizza are all alike, but it has a priority when it is associated with a Person (say I like Pizza more than omelet, depends on me not on Pizza or Omelet).
So you have a Preference
and Person
object.
Now Preference will vary from Person to Person so you will associate Preference with Person.
Since priority is very much dependent on Person you have multiple options to achieve:
- Use PriorityQueue - While adding Preference assign the priority. This queue will be present in Person class itself
- Use Custom Comparator (As suggested by @assylias)
- Add Rules to Preference(based on location, gender, e.t.c.) and have pre configured rules which when given certain criteria will return the preference as calculated by System, though have a manual override of this.
In this case you can just use
PriorityQueue
.

- 20,107
- 7
- 46
- 63