Free cookie consent management tool by TermsFeed Policy Generator

Ignore:
Timestamp:
04/26/16 00:02:05 (8 years ago)
Author:
abeham
Message:

#2457: worked on recommendation algorithms (x-validation)

File:
1 edited

Legend:

Unmodified
Added
Removed
  • branches/PerformanceComparison/HeuristicLab.OptimizationExpertSystem.Common/3.3/KnowledgeCenter.cs

    r13791 r13794  
    718718        result[problemMap[pr.Key]] = new Dictionary<long, int>();
    719719
    720         var indexMap = new BidirectionalDictionary<long, int>();
    721         var perf = new Dictionary<long, double>();
    722         var idx = 0;
    723         foreach (var kvp in pr.GroupBy(x => algorithmId2RunMapping.GetBySecond(x).Single())) {
    724           var ert = ExpectedRuntimeHelper.CalculateErt(kvp.ToList(), "QualityPerEvaluations", GetTarget(bkq, max), max).ExpectedRuntime;
    725           if (double.IsNaN(ert)) {
    726             // algorithm can't solve that instance with the given target
    727             // these are put into their own additional class
    728             result[problemMap[pr.Key]][kvp.Key] = nClasses;
    729             continue;
    730           }
    731           indexMap.Add(kvp.Key, idx);
    732           perf[kvp.Key] = Math.Log10(ert);
    733           idx++;
    734         }
    735         if (perf.Count == 0) continue;
    736        
    737         var points = perf.OrderBy(x => indexMap.GetByFirst(x.Key)).Select(x => x.Value).ToArray();
    738         int[] clusters;
    739         Ckmeans1dClusters(points, nClasses, out clusters);
    740         var ranks = clusters.Select((c, i) => new { Cluster = c, Perf = perf[indexMap.GetBySecond(i)] })
    741                             .GroupBy(x => x.Cluster, x => x.Perf)
    742                             .Select(x => new { Cluster = x.Key, AvgPerf = x.Average() })
    743                             .OrderBy(x => x.AvgPerf)
    744                             .Select((c, i) => new { Cluster = c.Cluster, Rank = i })
    745                             .ToDictionary(x => x.Cluster, x => x.Rank);
    746         for (var i = 0; i < clusters.Length; i++)
    747           result[problemMap[pr.Key]][indexMap.GetBySecond(i)] = ranks[clusters[i]];
     720        var values = pr.GroupBy(x => algorithmId2RunMapping.GetBySecond(x).Single())
     721                       .ToDictionary(x => x.Key, x => ExpectedRuntimeHelper.CalculateErt(x.ToList(), "QualityPerEvaluations", GetTarget(bkq, max), max).ExpectedRuntime);
     722        var ranks = ClusteringHelper<long>.Cluster(nClasses, values, x => double.IsNaN(x.Value))
     723          .GetByCluster().ToList();
     724        var minRank = ranks.Min(x => x.Key);
     725        foreach (var c in ranks) {
     726          foreach (var a in c.Value)
     727            result[problemMap[pr.Key]][a.Key] = c.Key == nClasses ? c.Key : c.Key - minRank;
     728        }
    748729      }
    749730      return result;
     
    772753    }
    773754
    774     // implement further classes and methods
    775     private static SortedList<double, int> Ckmeans1dClusters(double[] estimations, int k, out int[] clusterValues) {
    776       int nPoints = estimations.Length;
    777       var distinct = estimations.Distinct().OrderBy(x => x).ToArray();
    778       var max = distinct.Max();
    779       if (distinct.Length <= k) {
    780         var dict = distinct.Select((v, i) => new { Index = i, Value = v }).ToDictionary(x => x.Value, y => y.Index);
    781         for (int i = distinct.Length; i < k; i++)
    782           dict.Add(max + i - distinct.Length + 1, i);
    783 
    784         clusterValues = new int[nPoints];
    785         for (int i = 0; i < nPoints; i++)
    786           if (!dict.ContainsKey(estimations[i])) clusterValues[i] = 0;
    787           else clusterValues[i] = dict[estimations[i]];
    788 
    789         return new SortedList<double, int>(dict);
    790       }
    791 
    792       var n = distinct.Length;
    793       var D = new double[n, k];
    794       var B = new int[n, k];
    795 
    796       for (int m = 0; m < k; m++) {
    797         for (int j = m; j <= n - k + m; j++) {
    798           if (m == 0)
    799             D[j, m] = SumOfSquaredDistances(distinct, 0, j + 1);
    800           else {
    801             var minD = double.MaxValue;
    802             var minI = 0;
    803             for (int i = 1; i <= j; i++) {
    804               var d = D[i - 1, m - 1] + SumOfSquaredDistances(distinct, i, j + 1);
    805               if (d < minD) {
    806                 minD = d;
    807                 minI = i;
    808               }
    809             }
    810             D[j, m] = minD;
    811             B[j, m] = minI;
    812           }
    813         }
    814       }
    815 
    816       var centers = new SortedList<double, int>();
    817       var upper = B[n - 1, k - 1];
    818       var c = Mean(distinct, upper, n);
    819       centers.Add(c, k - 1);
    820       for (int i = k - 2; i >= 0; i--) {
    821         var lower = B[upper - 1, i];
    822         var c2 = Mean(distinct, lower, upper);
    823         centers.Add(c2, i);
    824         upper = lower;
    825       }
    826 
    827       clusterValues = new int[nPoints];
    828       for (int i = 0; i < estimations.Length; i++) {
    829         clusterValues[i] = centers.MinItems(x => Math.Abs(estimations[i] - x.Key)).First().Value;
    830       }
    831 
    832       return centers;
    833     }
    834 
    835     private static double SumOfSquaredDistances(double[] x, int start, int end) {
    836       if (start == end) throw new InvalidOperationException();
    837       if (start + 1 == end) return 0.0;
    838       double mean = 0.0;
    839       for (int i = start; i < end; i++) {
    840         mean += x[i];
    841       }
    842       mean /= (end - start);
    843       var sum = 0.0;
    844       for (int i = start; i < end; i++) {
    845         sum += (x[i] - mean) * (x[i] - mean);
    846       }
    847       return sum;
    848     }
    849 
    850     private static double Mean(double[] x, int start, int end) {
    851       if (start == end) throw new InvalidOperationException();
    852       double mean = 0.0;
    853       for (int i = start; i < end; i++) {
    854         mean += x[i];
    855       }
    856       mean /= (end - start);
    857       return mean;
    858     }
    859 
    860     public IEnumerable<Tuple<IAlgorithm, double>> GetAlgorithmInstanceRanking() {
     755    public IEnumerable<KeyValuePair<IAlgorithm, double>> GetAlgorithmInstanceRanking() {
    861756      return RecommendationModel.GetRanking(ProblemInstances.Single(IsCurrentInstance));
    862757    }
Note: See TracChangeset for help on using the changeset viewer.