Start line:  
End line:  

Snippet Preview

Snippet HTML Code

Stack Overflow Questions
  /*
   * RecommenderEvaluator.java
   * 
   * Copyright (C) 2013 Alessandro Negro <alessandro.negro at reco4j.org>
   *
   * This program is free software: you can redistribute it and/or modify
   * it under the terms of the GNU General Public License as published by
   * the Free Software Foundation, either version 3 of the License, or
   * (at your option) any later version.
  *
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  * GNU General Public License for more details.
  *
  * You should have received a copy of the GNU General Public License
  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
  */
 package org.reco4j.recommender;
 
 import java.io.File;
 import java.io.Writer;
 import java.util.List;
 import java.util.Map;

Author(s):
Alessandro Negro <alessandro.negro at reco4j.org>
 
 public class RecommenderEvaluator
 {
   public static final int RANDOM_TEST_SIZE = 100;
 
   public static void evaluateRecommender(IGraph testDataSetIRecommender recommender)
   {
     IRecommenderConfig config = recommender.getConfig();
     List<INodeusers = testDataSet.getNodesByType(config.getUserType());
     evaluateRecommender(usersrecommender);
   }
 
   public static void evaluateRecommender(UserItemDataset userItemDatasetIRecommender recommender)
   {
     evaluateRecommender(userItemDataset.getUserList().values(), recommender);
   }
 
   public static void evaluateRecommender(Collection<INodeusersIRecommender recommender)
   {
     IRecommenderConfig config = recommender.getConfig();
     int n = 0;
     double numerator = 0.0;
     for (INode user : users)
     {
       //System.out.println("User: " + user.getProperty(config.getUserIdentifierName()));
       List<IEdgeranks = user.getOutEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig()));
       if (ranks.isEmpty())
         continue;
       for (IEdge rank : ranks)
       {
         StringBuilder output = new StringBuilder();
         output.append("item: ").append(rank.getDestination().getProperty(config.getItemIdentifierName()));
         double estimatedRating = recommender.estimateRating(userrank.getDestination());
         if (estimatedRating > 0)
         {
           n++;
           double realValue = Double.parseDouble(rank.getProperty(config.getEdgeRankValueName()));
           double difference = realValue - estimatedRating;
           numerator = numerator + Math.abs(difference);
           output.append(" n: ").append(n).append(" numerator: ").append(numerator).append(" estimatedRating: ").append(estimatedRating).append(" realValue: ").append(realValue).append(" difference: ").append(difference);
 
 
           ..println(output);
         }
         ..flush();
       }
 
     }
     double mae = numerator / (double) (n);
     ..println("MAE: " + mae);
   }
 
   public static void evaluateBinaryRecommender(IGraph testDataSetIRecommender recommender)
   {
     IRecommenderConfig config = recommender.getConfig();
     List<INodeusers = testDataSet.getNodesByType(config.getUserType());
     SummaryStatistics statistics = new SummaryStatistics();
    int n = 0;
    for (INode user : users)
    {
      int preferredItems = 0;
      double numerator = 0.0;
      List<Ratingrecommends = recommender.recommend(user);
      //System.out.println("User: " + user.getProperty(config.getUserIdentifierName()));
      List<IEdgeranks = user.getOutEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig()));
      if (ranks.isEmpty())
        continue;
      for (IEdge rank : ranks)
      {
        preferredItems++;
        for (int i = 0; i < recommends.size(); i++)
        {
          Rating reco = recommends.get(i);
          if (reco.getItemID() == rank.getDestination().getId())
          {
            numerator += reco.getRate();
            recommends.remove(i);
          }
        }
      }
      double ap = numerator / (doublepreferredItems;
      ..println("Ap for user " + user.getId() + ": " + ap);
      statistics.addValue(ap);
    }
    double map = statistics.getMean();
    ..println("MAP: " + map);
    ..println("MIN AP: " + statistics.getMin());
    ..println("MAX AP: " + statistics.getMax());
  }
  public static void evaluateTopN(Collection<INodeitemsIRecommender recommender)
  {
    IRecommenderConfig config = recommender.getConfig();
    for (INode item : items)
    {
      //If there is no history I can't compute the future
      if (!item.getInEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig())).isEmpty())
      {
        List<IEdgeinEdges = item.getInEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig()));
        int realHit = 0;
        int predictedHit = 0;
//        double minEstimate = 10.0;
//        double maxEstimate = 0.0;
        for (IEdge interest : inEdges)
        {
          //If there is no history for the user
          if (interest.getSource().getOutEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig())).isEmpty())
          {
            //System.out.println("For user: "+ interest.getSource().getProperty(config.getUserIdentifierName()) + " there is no history!");
            continue;
          }
          realHit++;
          List<Ratingrecommends = recommender.recommend(interest.getSource());
          int pos = 0;
          for (Rating rating : recommends)
          {
            pos++;
            if (rating.getItem().getId() == item.getId())
            {
              predictedHit++;
              ..println("Pos: " + pos + " estimated: " + rating.getRate());
              break;
            }
          }
//          double estimateBinaryRating = recommender.estimateRating(interest.getSource(), item);
//          if (estimateBinaryRating > 0.02)//Inserire valore soglia
//          {
//            predictedHit++;
//            if (estimateBinaryRating < minEstimate)
//              minEstimate = estimateBinaryRating;
//            if (estimateBinaryRating > maxEstimate)
//              maxEstimate = estimateBinaryRating;
//          
//          }
//          System.out.println("Product: " + item.getProperty(config.getItemIdentifierName())
//                             + " choosen by user:  " + interest.getSource().getProperty(config.getUserIdentifierName())
//                             + " estimated ratings: " + recommender.estimateBinaryRating(interest.getSource(), item));
        }
        ..println("Product: " + item.getProperty(config.getItemIdentifierName())
                + " ->  " + predictedHit + " / " + realHit);
      } else
      {
        //System.out.println("For product: "+ item.getProperty(config.getItemIdentifierName()) + " there is no history!");
      }
    }
  }
  public static void evaluateTopN(Collection<INodeusersBaseCollection<INodeusersHitINode itemIRecommender recommenderint limit)
  {
    IRecommenderConfig config = recommender.getConfig();
    List<RatingrecommendedUser = recommender.recommendInterestedUsers(usersBaseitemlimit);
    List<List<Rating>> randomUserSet = new ArrayList<List<Rating>>();
    int[] randomHits = new int[];
    
    for (int i = 0; i < i++)
      randomUserSet.add(recommender.recommendRandomUsers(usersBaseitemlimit));
    int realHit = 0;
    int predictedHit = 0;
    for (INode user : usersHit)
    {
      //If there is no history I can't compute the future
      if (!user.getOutEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig())).isEmpty())
      {
        realHit++;
        for (Rating rate : recommendedUser)
          if (rate.getUser().getId() == user.getId())
            predictedHit++;
        for (int i = 0; i < i++)
        {
          List<RatingrandomUser = randomUserSet.get(i);
        
          for (Rating rate : randomUser)
            if (rate.getUser().getId() == user.getId())
              randomHits[i]++;
        }
      }
    }
    
    SummaryStatistics randomUserStats = new SummaryStatistics();
    for (int i = 0; i < i++)
      randomUserStats.addValue((doublerandomHits[i]);
//      randomUserStats.addValue(((double) randomHits[i] / (double) realHit) * 100 );
    
    ..println("Product: " + item.getProperty(config.getItemIdentifierName()));
    ..println("Reco4J: " + predictedHit + " / " + realHit + " = " + ((doublepredictedHit / (doublerealHit) * 100 + "% ");
    ..println("Random (" +  + " extractions):  " + randomUserStats.getMean() + " / " + realHit + " = (mean) " + ((doublerandomUserStats.getMean() / (doublerealHit) * 100 + "% ± (standard deviation) " + ((doublerandomUserStats.getStandardDeviation()/ (doublerealHit) * 100 + "%");
  }
  public static void evaluateTopNWithPosition(Collection<INodeusersBaseMap<LongINodeusersHitINode itemIRecommender recommenderthrows FileNotFoundException
  {
    IRecommenderConfig config = recommender.getConfig();
    ..println("usersBase.size(): " + usersBase.size());
    ..println("Product: " + item.getProperty(config.getItemIdentifierName()));
    
    List<RatingrecommendedUser = recommender.recommendInterestedUsers(usersBaseitemusersBase.size());
    ..println("recommendedUser.size(): " + recommendedUser.size());
    
    PrintWriter output = new PrintWriter("/tmp/evaluation" + item.getProperty(config.getItemIdentifierName()).replace("\"""_") + ".csv");
    
    StringBuilder fileHeader = new StringBuilder();
//    fileHeader.append("Position;Positive Mean;Positive Min;Positive Max; Positive Number; Negative Mean; Negative Min; Negative Max; Negative Number");
    fileHeader.append("Quantity;;;;Position;;;");
    fileHeader.append("\n");
    fileHeader.append("%;Total;Positives;Negatives;Positives Mean;Positives St. Dev.;Negatives Mean;Negatives St. Dev.");
    fileHeader.append("\n");
    output.write(fileHeader.toString());
    
    int chunksCount = 20;
    int[] chunks = new int[chunksCount];
    int[] chunkPercentages = new int[chunksCount];
    double chunksSize = (doubleusersBase.size() / (doublechunksCount;
    double chunksSizePercentage = (double) 100 / (doublechunksCount;
    for (int i = 1; i < chunksCounti++)
    {
      chunks[i - 1] = (int) (chunksSize * (doublei);
      chunkPercentages[i - 1] = (int) (chunksSizePercentage * (doublei);
    }
    
    chunks[chunksCount - 1] = usersBase.size();
    chunkPercentages[chunksCount - 1] = 100;
    
    int position = 0;
    int currentChunk = 0;
    SummaryStatistics positiveSummary = new SummaryStatistics();
    SummaryStatistics negativeSummary = new SummaryStatistics();
    
    String atHitSizeRow = "NOT FOUND";
    
    for (Rating rate : recommendedUser)
    {
      position++; // is is 1-based, not 0-based, we "preincrement" it.
      
      if (usersHit.containsKey(rate.getUser().getId()))
        positiveSummary.addValue(position);
      else
        negativeSummary.addValue(position);
      if (position == chunks[currentChunk])
      {
        ..println("Position: " + position);
        ..println("Positive Position Mean: " + (intpositiveSummary.getMean() + " St. Dev.: " + (intpositiveSummary.getStandardDeviation() + " Number: " + positiveSummary.getN() + "\n" + 
                           "Negative Position Mean: " + (intnegativeSummary.getMean() + " St. Dev.: " + (intnegativeSummary.getStandardDeviation() + " Number: " + negativeSummary.getN() + "\n");
        
        StringBuilder row = new StringBuilder();
        // Quantity
        row.append(chunkPercentages[currentChunk]).append(";");
        row.append(chunks[currentChunk]).append(";");
        row.append((int)positiveSummary.getN()).append(";");
        row.append((int)negativeSummary.getN()).append(";");
        
        // Position
        row.append((int)positiveSummary.getMean()).append(";");
        row.append((int)positiveSummary.getStandardDeviation()).append(";");
        
        row.append((int)negativeSummary.getMean()).append(";");
        row.append((int)negativeSummary.getStandardDeviation()).append(";");
        
        row.append("\n");
        
        output.write(row.toString());
        
        currentChunk++; // 0-based
      }
      
      if (position == usersHit.size())
      {
        ..println("At Hit Size Position: " + position);
        ..println("Positive Position Mean: " + (intpositiveSummary.getMean() + " St. Dev.: " + (intpositiveSummary.getStandardDeviation() + " Number: " + positiveSummary.getN() + "\n" + 
                           "Negative Position Mean: " + (intnegativeSummary.getMean() + " St. Dev.: " + (intnegativeSummary.getStandardDeviation() + " Number: " + negativeSummary.getN() + "\n");
        
        StringBuilder row = new StringBuilder();
        // Quantity
        row.append((int)(((doubleposition / (doubleusersBase.size()) * 100)).append(";");
        row.append(position).append(";");
        row.append((int)positiveSummary.getN()).append(";");
        row.append((int)negativeSummary.getN()).append(";");
        
        // Position
        row.append((int)positiveSummary.getMean()).append(";");
        row.append((int)positiveSummary.getStandardDeviation()).append(";");
        
        row.append((int)negativeSummary.getMean()).append(";");
        row.append((int)negativeSummary.getStandardDeviation()).append(";");
        
        row.append("\n");
        
        atHitSizeRow = row.toString();
      }
      
      output.flush();
    }
    
    while (position < usersBase.size())
    {
      position++; // is is 1-based, not 0-based, we "preincrement" it.
      negativeSummary.addValue(position);
      // COPIATO E IDENTICO AL BLOCCO SOPRA!
      if (position == chunks[currentChunk])
      {
        ..println("Position: " + position);
        ..println("Positive Position Mean: " + (intpositiveSummary.getMean() + " St. Dev.: " + (intpositiveSummary.getStandardDeviation() + " Number: " + positiveSummary.getN() + "\n" + 
                           "Negative Position Mean: " + (intnegativeSummary.getMean() + " St. Dev.: " + (intnegativeSummary.getStandardDeviation() + " Number: " + negativeSummary.getN() + "\n");
        
        StringBuilder row = new StringBuilder();
        // Quantity
        row.append(chunkPercentages[currentChunk]).append(";");
        row.append(chunks[currentChunk]).append(";");
        row.append((int)positiveSummary.getN()).append(";");
        row.append((int)negativeSummary.getN()).append(";");
        
        // Position
        row.append((int)positiveSummary.getMean()).append(";");
        row.append((int)positiveSummary.getStandardDeviation()).append(";");
        
        row.append((int)negativeSummary.getMean()).append(";");
        row.append((int)negativeSummary.getStandardDeviation()).append(";");
        
        row.append("\n");
        
        output.write(row.toString());
        
        currentChunk++; // 0-based
      }
      
      if (position == usersHit.size())
      {
        ..println("At Hit Size Position: " + position);
        ..println("Positive Position Mean: " + (intpositiveSummary.getMean() + " St. Dev.: " + (intpositiveSummary.getStandardDeviation() + " Number: " + positiveSummary.getN() + "\n" + 
                           "Negative Position Mean: " + (intnegativeSummary.getMean() + " St. Dev.: " + (intnegativeSummary.getStandardDeviation() + " Number: " + negativeSummary.getN() + "\n");
        
        StringBuilder row = new StringBuilder();
        // Quantity
        row.append((int)(((doubleposition / (doubleusersBase.size()) * 100)).append(";");
        row.append(position).append(";");
        row.append((int)positiveSummary.getN()).append(";");
        row.append((int)negativeSummary.getN()).append(";");
        
        // Position
        row.append((int)positiveSummary.getMean()).append(";");
        row.append((int)positiveSummary.getStandardDeviation()).append(";");
        
        row.append((int)negativeSummary.getMean()).append(";");
        row.append((int)negativeSummary.getStandardDeviation()).append(";");
        
        row.append("\n");
        
        atHitSizeRow = row.toString();
      }
      
      output.flush();
    }
//    
//    StringBuilder row = new StringBuilder();
//    row.append(usersBase.size()).append(";");
//    row.append((int)positiveSummary.getMean()).append(";");
//    row.append((int)positiveSummary.getMin()).append(";");
//    row.append((int)positiveSummary.getMax()).append(";");
//    row.append((int)positiveSummary.getN()).append(";");
//    row.append((int)negativeSummary.getMean()).append(";");
//    row.append((int)negativeSummary.getMin()).append(";");
//    row.append((int)negativeSummary.getMax()).append(";");
//    row.append((int)negativeSummary.getN());
//    row.append("\n");
//    output.write(row.toString());
//    output.flush();
    
    StringBuilder row = new StringBuilder();
    row.append("\n");
    row.append("\n");
    row.append("\n");
    row.append("At Hit;(Total Acceptance)").append(";");
    row.append("\n");
    row.append(fileHeader.toString());
    row.append(atHitSizeRow.toString());
    output.write(row.toString());
    output.flush();
    output.close();
    ..println("Positive Mean Position: " + (intpositiveSummary.getMean() + " Min: " + (intpositiveSummary.getMin() + " Max: " + (intpositiveSummary.getMax() + "\n"
                     + "Negative Mean Position: " + (intnegativeSummary.getMean() + " Min: " + (intnegativeSummary.getMin() + " Max: " + (intnegativeSummary.getMax() + "\n");
  }
  public static void evaluateTopNIntersection(Collection<INodeusersBaseCollection<INodeusersHitINode itemIRecommender recommenderint limitString edgeName)
  {
    IRecommenderConfig config = recommender.getConfig();
    List<RatingrecommendedUser = recommender.recommendInterestedUsers(usersBaseitemlimit);
    int realHit = 0;
    int predictedHit = 0;
    int intersectionHit = 0;
    for (INode user : usersHit)
    {
      //If there is no history I can't compute the future
      if (!user.getOutEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig())).isEmpty())
      {
        realHit++;
        for (Rating rate : recommendedUser)
        {
          if (rate.getUser().getId() == user.getId())
          {
            intersectionHit++;
            if (user.getEdge(item, EdgeTypeFactory.getEdgeType(edgeName)).getProperty("accept").equalsIgnoreCase("yes"))
              predictedHit++;
          }
        }
      }
    }
    ..println("Product: " + item.getProperty(config.getItemIdentifierName())
            + " ->  " + predictedHit + " / " + intersectionHit + "/" + realHit + " = " + ((doublepredictedHit / (doublerealHit) * 100 + "%");
  }
  public static void oldevaluateRecommender(IGraph testDataSetIRecommender reco)
  {
    IRecommenderConfig config = reco.getConfig();
    int hitRecommed = 0;
    int userNumber = 0;
    List<INodeusers = testDataSet.getNodesByType(config.getUserType());
    for (INode user : users)
    {
      List<IEdgeranks = user.getOutEdge(EdgeTypeFactory.getEdgeType(.config.getGraphConfig()));
      if (ranks.isEmpty())
        continue;
      userNumber++;
      List<Ratingrecommendtations = reco.recommend(user);
      ..println("Recommendation for User with code: "
              + user.getProperty(config.getUserIdentifierName()));
      int hit = 0;
      for (Rating rate : recommendtations)
      {
        for (IEdge edge : ranks)
        {
          String recommendedId = rate.getItem().getProperty(config.getItemIdentifierName());
          String testRankId = edge.getSource().getProperty(config.getItemIdentifierName());
          if (recommendedId.equalsIgnoreCase(testRankId));
          hit++;
        }
      }
      ..println("Hit Number for user "
              + user.getProperty(config.getUserIdentifierName())
              + " = " + hit);
      if (hit > 0)
        hitRecommed++;
    }
    ..println("Hit percentage: " + (userNumber > 0 ? (doublehitRecommed / (doubleuserNumber : 0));
  }
New to GrepCode? Check out our FAQ X