Free cookie consent management tool by TermsFeed Policy Generator

Ignore:
Timestamp:
02/20/14 17:45:06 (10 years ago)
Author:
gkronber
Message:

#2125 fixed the bug that covariance functions returned the full gradient vector even when parameters are partially fixed.
changed the calculation of NN covariance and gradient to direct calculation (instead of AutoDiff)

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/sources/HeuristicLab.Algorithms.DataAnalysis/3.4/GaussianProcess/CovarianceFunctions/CovarianceNeuralNetwork.cs

    r9542 r10489  
    4343      get { return (IValueParameter<DoubleValue>)Parameters["Length"]; }
    4444    }
     45    private bool HasFixedScaleParameter {
     46      get { return ScaleParameter.Value != null; }
     47    }
     48    private bool HasFixedLengthParameter {
     49      get { return LengthParameter.Value != null; }
     50    }
    4551
    4652    [StorableConstructor]
     
    6874    public int GetNumberOfParameters(int numberOfVariables) {
    6975      return
    70         (ScaleParameter.Value != null ? 0 : 1) +
    71         (LengthParameter.Value != null ? 0 : 1);
     76        (HasFixedScaleParameter ? 0 : 1) +
     77        (HasFixedLengthParameter ? 0 : 1);
    7278    }
    7379
     
    8389      // gather parameter values
    8490      int c = 0;
    85       if (LengthParameter.Value != null) {
     91      if (HasFixedLengthParameter) {
    8692        length = LengthParameter.Value.Value;
    8793      } else {
     
    9096      }
    9197
    92       if (ScaleParameter.Value != null) {
     98      if (HasFixedScaleParameter) {
    9399        scale = ScaleParameter.Value.Value;
    94100      } else {
     
    110116      double length, scale;
    111117      GetParameterValues(p, out scale, out length);
    112       // create functions
    113       AutoDiff.Variable p0 = new AutoDiff.Variable();
    114       AutoDiff.Variable p1 = new AutoDiff.Variable();
    115       var l = TermBuilder.Exp(2.0 * p0);
    116       var s = TermBuilder.Exp(2.0 * p1);
    117       AutoDiff.Variable[] x1 = new AutoDiff.Variable[columnIndices.Count()];
    118       AutoDiff.Variable[] x2 = new AutoDiff.Variable[columnIndices.Count()];
    119       AutoDiff.Term sx = 1;
    120       AutoDiff.Term s1 = 1;
    121       AutoDiff.Term s2 = 1;
    122       for (int k = 0; k < columnIndices.Count(); k++) {
    123         x1[k] = new AutoDiff.Variable();
    124         x2[k] = new AutoDiff.Variable();
    125         sx += x1[k] * x2[k];
    126         s1 += x1[k] * x1[k];
    127         s2 += x2[k] * x2[k];
    128       }
    129 
    130       var parameter = x1.Concat(x2).Concat(new AutoDiff.Variable[] { p0, p1 }).ToArray();
    131       var values = new double[x1.Length + x2.Length + 2];
    132       var c = (s * asin(sx / (sqrt((l + s1) * (l + s2))))).Compile(parameter);
     118      var fixedLength = HasFixedLengthParameter;
     119      var fixedScale = HasFixedScaleParameter;
    133120
    134121      var cov = new ParameterizedCovarianceFunction();
    135122      cov.Covariance = (x, i, j) => {
    136         int k = 0;
     123        double sx = 1.0;
     124        double s1 = 1.0;
     125        double s2 = 1.0;
    137126        foreach (var col in columnIndices) {
    138           values[k] = x[i, col];
    139           k++;
     127          sx += x[i, col] * x[j, col];
     128          s1 += x[i, col] * x[i, col];
     129          s2 += x[j, col] * x[j, col];
    140130        }
    141         foreach (var col in columnIndices) {
    142           values[k] = x[j, col];
    143           k++;
    144         }
    145         values[k] = Math.Log(Math.Sqrt(length));
    146         values[k + 1] = Math.Log(Math.Sqrt(scale));
    147         return c.Evaluate(values);
     131
     132        return (scale * Math.Asin(sx / (Math.Sqrt((length + s1) * (length + s2)))));
    148133      };
    149134      cov.CrossCovariance = (x, xt, i, j) => {
    150         int k = 0;
     135        double sx = 1.0;
     136        double s1 = 1.0;
     137        double s2 = 1.0;
    151138        foreach (var col in columnIndices) {
    152           values[k] = x[i, col];
    153           k++;
     139          sx += x[i, col] * xt[j, col];
     140          s1 += x[i, col] * x[i, col];
     141          s2 += xt[j, col] * xt[j, col];
    154142        }
     143
     144        return (scale * Math.Asin(sx / (Math.Sqrt((length + s1) * (length + s2)))));
     145      };
     146      cov.CovarianceGradient = (x, i, j) => GetGradient(x, i, j, length, scale, columnIndices, fixedLength, fixedScale);
     147      return cov;
     148    }
     149
     150    // order of returned gradients must match the order in GetParameterValues!
     151    private static IEnumerable<double> GetGradient(double[,] x, int i, int j, double length, double scale, IEnumerable<int> columnIndices,
     152      bool fixedLength, bool fixedScale) {
     153      {
     154        double sx = 1.0;
     155        double s1 = 1.0;
     156        double s2 = 1.0;
    155157        foreach (var col in columnIndices) {
    156           values[k] = xt[j, col];
    157           k++;
     158          sx += x[i, col] * x[j, col];
     159          s1 += x[i, col] * x[i, col];
     160          s2 += x[j, col] * x[j, col];
    158161        }
    159         values[k] = Math.Log(Math.Sqrt(length));
    160         values[k + 1] = Math.Log(Math.Sqrt(scale));
    161         return c.Evaluate(values);
     162        var h = (length + s1) * (length + s2);
     163        var f = sx / Math.Sqrt(h);
     164        if (!fixedLength) {
     165          yield return -scale / Math.Sqrt(1.0 - f * f) * ((length * sx * (2.0 * length + s1 + s2)) / Math.Pow(h, 3.0 / 2.0));
     166        }
     167        if (!fixedScale) {
     168          yield return 2.0 * scale * Math.Asin(f);
     169        }
     170
    162171      };
    163       cov.CovarianceGradient = (x, i, j) => {
    164         int k = 0;
    165         foreach (var col in columnIndices) {
    166           values[k] = x[i, col];
    167           k++;
    168         }
    169         foreach (var col in columnIndices) {
    170           values[k] = x[j, col];
    171           k++;
    172         }
    173         values[k] = Math.Log(Math.Sqrt(length));
    174         values[k + 1] = Math.Log(Math.Sqrt(scale));
    175         return c.Differentiate(values).Item1.Skip(columnIndices.Count() * 2);
    176       };
    177       return cov;
    178172    }
    179173
Note: See TracChangeset for help on using the changeset viewer.