0
@Override
    public Collection<Dish> getDishesContaining(Collection<Ingredient> ingredients) throws DatabaseException {
        Collection<Dish> result = new ArrayList<>();
        for (Dish currentDish : this.getAll()) {
            if (currentDish.containsIngredient(ingredients)!=0) {
                result.add(currentDish);
            }
        }
        return result;
    }

Overview:

  • Dish -> Param: ArrayList<Ingredient> ingredients

  • Dish -> Funct: containsIngredient(Collection<Ingredient> ingredients) : int (returns int percentage howmany ingredients the given collection has with the dish)

Example:

  • For given Ingrediënt Collection= [X,Y,Z]

    • Dish A = [Ingredients:[X,Y,Z]], -> dishA.containsIngredient(ingredientCollection) =1

    • Dish B = [Ingredients:[W,X,Y,Z]], -> dishB.containsIngredient(ingredientCollection) = 0,75

    • Dish C = [Ingredients:[U,V,W]]; -> dishC.containsIngredient(ingredientCollection) = 0

Question

I want to return a Collection of all the dishes that contain the given ingredients orderd with the ones that have the highest percentage of common ingredients first. i was thinking of writing a Collection class of wich i add an extra param to the 'add' funct of the percentage. But this seems abit far fetched. Am i missing on something ?

MrMe TumbsUp
  • 416
  • 1
  • 4
  • 17

1 Answers1

0

The clean, Object Oriented way to solve this problem is to implement the java.lang.Comparable interface for your object. Then, you can use any of the ordering methods provided by the Collections class.

I changed your spec a little: instead of having a containsIngredient(Collection ingredients) method, I'm storing the state of the ingredients in the dish object itself. This makes it easier to compare to other dish objects.

So, your above for loop would be:

    for (Dish currentDish : this.getAll()) {
        currentDish.setIngredients(ingredients);
        if (currentDish.getPercentageOfIngredientsContained() != 0) {
            result.add(currentDish);
        }
    }

And here's what a Dish class which implements Comparable looks like:

import java.util.ArrayList;
import java.lang.Comparable;

public class Dish implements Comparable<Dish> {

  ArrayList<Ingredient> _ingredients = null;
  int _percentageOfIngredientsContained = 0;

  public ArrayList<Ingredient> getIngredients() {
    return _ingredients;
  }

  public void setIngredients(ArrayList<Ingredient> ingredients) {
    _ingredients = ingredients;
    computeIngredientsContained();
  }

  public int getPercentageOfIngredientsContained() {
    return _percentageOfIngredientsContained;
  }

  private void computeIngredientsContained() {
    int percent = 0;

    // Calculate percentage by looking at _ingredients...
    // ...
    // ...

    _percentageOfIngredientsContained = percent;    
  }

  // Implement Comparable
  @Override
  public int compareTo(Dish anotherDishObject) {
    if (this.getPercentageOfIngredientsContained() < anotherDishObject.getPercentageOfIngredientsContained()) {
      return -1;
    }
    else if (this.getPercentageOfIngredientsContained() == anotherDishObject.getPercentageOfIngredientsContained()) {
      return 0;
    }
    else {
      return 1;
    }
  }
}

With Dish implemented this way, you can sort any list of dishes using Collections.sort(dishes), and they'll be sorted by percentage of ingredients contained.

Anna Dickinson
  • 3,307
  • 24
  • 43
  • Tell me, `currentDish.getPercentageOfIngredientsContained()` how do you calculate a percentage of that ? The goal of that function was to calculate howmuch the given Collection of ingredients has in common with the dish. – MrMe TumbsUp May 05 '14 at 12:11
  • I'm not gonna write *all* the code for ya... :-p Try representing the ingredients as Sets. (java.util.HashSet) Find the intersection of the sets. Divide the number of ingredients in the intersection set by the total number of ingredients for a particular dish. – Anna Dickinson May 05 '14 at 15:50