List of usage examples for org.apache.mahout.cf.taste.impl.recommender GenericItemBasedRecommender recommendedBecause
@Override public List<RecommendedItem> recommendedBecause(long userID, long itemID, int howMany) throws TasteException
From source file:ContentBasedRecommender.java
License:Apache License
/** * Method the creates a list of recommendations. * Already rated stories are excluded, as are stories present in the front end array if add="true" * // w w w.ja v a2 s .co m * @throws TasteException thrown if there if something went wrong with Mahout */ public void runContentBasedRecommender() throws TasteException { /*Find out where this file is located*/ try { fileLocation = new File(this.getClass().getProtectionDomain().getCodeSource().getLocation().toURI()); } catch (URISyntaxException e) { e.printStackTrace(); } /*"content"+userId is the name of the view we shall create*/ conn.setConnection(); /*Create a temporary view the includes all preferences values for this user*/ conn.createView((int) userId); /*Sets the dataModel based on the data in the created view*/ conn.setDataModel(); DataModel model = conn.getDataModel(); /*Gets all the info from the similarites.csv file into a list of objects accepted by Mahout*/ Collection<ItemItemSimilarity> sim = getStorySimilarities(); /*GenericItemBasedRecommender need an ItemSimilarity-object as input, so create an instance of this class.*/ ItemSimilarity similarity = new GenericItemSimilarity(sim); /*Create a new Recommender-instance with our datamodel and story similarities*/ GenericItemBasedRecommender recommender = new GenericItemBasedRecommender(model, similarity); /* Compute the recommendations. model.getNumItems() is the number of recommendations we want (we don't really want that many, * but we don't know how many of the top items the user already have rated), don't worry about the null, * and true tells the recommender that we want to include already known items*/ List<RecommendedItem> recommendations = recommender.recommend(userId, model.getNumItems(), null, true); /*Find the stories that the user have rated*/ HashMap<Integer, Integer> ratedStories = conn.getRated((int) userId); ArrayList<Integer> frontendStories = new ArrayList<>(); /* Find the stories already present in the recommendations list at front end * These stories should not be recommended again*/ if (add.equals("true")) { frontendStories = conn.getStoriesInFrontendArray((int) userId); } int ranking = 1; Random rand = new Random(); int randomDislikedRanking = rand.nextInt(6) + 5; ArrayList<DatabaseInsertObject> itemsToBeInserted = new ArrayList<>(); ArrayList<Long> idsToBeInserted = new ArrayList<>(); for (RecommendedItem recommendation : recommendations) { /* To get a story outside of the users preferences, finds the least recommended story */ if (randomDislikedRanking == ranking) { /*Make sure the false recommendation is not already in the front end array or already among the top ten recommendation (may happen if the user doesn't have many not seen/not rated stories left) */ for (int i = 1; i < recommendations.size(); i++) { long dislikedStoryId = recommendations.get(recommendations.size() - i).getItemID(); if (!frontendStories.contains((int) dislikedStoryId) && !idsToBeInserted.contains(dislikedStoryId) && ratedStories.get((int) dislikedStoryId) == null) { itemsToBeInserted.add(new DatabaseInsertObject((int) userId, "DF." + dislikedStoryId, "FalseRecommendation", 1, 0, ranking, recommendations.get(recommendations.size() - i).getValue())); idsToBeInserted.add(dislikedStoryId); System.out.print("False recommend: "); System.out.println(dislikedStoryId); break; } } ranking++; if (ranking > 10) { break; } continue; } /*If the item has not been rated,is not already in the recommendation list at front end or already a false recommendation we insert it*/ if ((ratedStories.get((int) recommendation.getItemID()) == null) && !frontendStories.contains((int) recommendation.getItemID()) && !idsToBeInserted.contains(recommendation.getItemID())) { /*Get the 30 items that had most influence on the recommendation*/ List<RecommendedItem> becauseItems = recommender.recommendedBecause(userId, recommendation.getItemID(), 30); int counter = 1; ArrayList<RecommendedItem> explanationItems = new ArrayList<>(); for (RecommendedItem because : becauseItems) { /*Add story to explanation if this story has been rated and the rating is good*/ if (!explanationItems.contains(because) && ratedStories.get((int) because.getItemID()) != null && ratedStories.get((int) because.getItemID()) > 2) { explanationItems.add(because); counter++; } if (counter > 3) { break; } } /*Gets the titles of the explanation-stories and creates a string*/ String explanation = conn.createExplanation(explanationItems); itemsToBeInserted.add(new DatabaseInsertObject((int) userId, "DF." + recommendation.getItemID(), explanation, 0, 0, ranking, recommendation.getValue())); idsToBeInserted.add(recommendation.getItemID()); System.out.println(recommendation); ranking++; } /*When we got 10 new recommendations, we're happy*/ if (ranking > 10) { break; } } this.recommendations = recommendations; /*Delete the current recommendations stored in stored_story that has not been seen by the user*/ conn.deleteRecommendations((int) userId); /*Insert the 10 items we found*/ conn.insertUpdateRecommendValues(itemsToBeInserted); /*Drop our temporary view*/ conn.dropView(); conn.closeConnection(); }