Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/AbstractFeatureCorrelationCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/AbstractFeatureCorrelationCalculator.cs	(revision 13938)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/AbstractFeatureCorrelationCalculator.cs	(revision 13938)
@@ -0,0 +1,138 @@
+﻿#region License Information
+
+/* HeuristicLab
+ * Copyright (C) 2002-2016 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab 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.
+ *
+ * HeuristicLab 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 HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#endregion
+
+using System;
+using System.Collections.Generic;
+using System.ComponentModel;
+using System.Linq;
+using HeuristicLab.PluginInfrastructure;
+
+namespace HeuristicLab.Problems.DataAnalysis.Views {
+  [NonDiscoverableType]
+  public abstract class AbstractFeatureCorrelationCalculator {
+    private readonly BackgroundWorker backgroundWorker;
+
+    public AbstractFeatureCorrelationCalculator() {
+      backgroundWorker = new BackgroundWorker { WorkerReportsProgress = true, WorkerSupportsCancellation = true };
+
+      backgroundWorker.DoWork += BackgroundWorker_DoWork;
+      backgroundWorker.ProgressChanged += BackgroundWorker_ProgressChanged;
+      backgroundWorker.RunWorkerCompleted += BackgroundWorker_RunWorkerCompleted;
+    }
+
+    private BackgroundWorkerInfo bwInfo;
+    public void TryCancelCalculation() {
+      if (!backgroundWorker.IsBusy) return;
+
+      bwInfo = null;
+      backgroundWorker.CancelAsync();
+    }
+
+    protected static IEnumerable<int> GetRelevantIndices(IDataAnalysisProblemData problemData, string partition) {
+      IEnumerable<int> var;
+      if (partition.Equals(AbstractFeatureCorrelationView.TRAININGSAMPLES))
+        var = problemData.TrainingIndices;
+      else if (partition.Equals(AbstractFeatureCorrelationView.TESTSAMPLES))
+        var = problemData.TestIndices;
+      else var = Enumerable.Range(0, problemData.Dataset.Rows);
+      return var;
+    }
+
+    #region backgroundworker
+
+    protected void StartCalculation(BackgroundWorkerInfo info) {
+      bwInfo = info;
+      if (backgroundWorker.IsBusy) {
+        backgroundWorker.CancelAsync();
+        return;
+      }
+
+      backgroundWorker.RunWorkerAsync(bwInfo);
+    }
+
+    protected abstract void BackgroundWorker_DoWork(object sender, DoWorkEventArgs e);
+
+    private void BackgroundWorker_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) {
+      BackgroundWorker worker = (BackgroundWorker)sender;
+      if (!e.Cancelled && !worker.CancellationPending) {
+        if (e.Error != null) {
+          ErrorHandling.ShowErrorDialog(e.Error);
+        } else {
+          OnCorrelationCalculationFinished((double[,])e.Result, bwInfo.Calculator, bwInfo.Partition, bwInfo.IgnoreMissingValues, bwInfo.Variable);
+        }
+      } else if (bwInfo != null) {
+        backgroundWorker.RunWorkerAsync(bwInfo);
+      }
+    }
+
+    #endregion
+
+    #region events
+    public class CorrelationCalculationFinishedArgs : EventArgs {
+      public double[,] Correlation { get; private set; }
+      public IDependencyCalculator Calculcator { get; private set; }
+      public string Partition { get; private set; }
+      public bool IgnoreMissingValues { get; private set; }
+      public string Variable { get; private set; }
+
+
+      public CorrelationCalculationFinishedArgs(double[,] correlation, IDependencyCalculator calculator, string partition, bool ignoreMissingValues, string variable = null) {
+        this.Correlation = correlation;
+        this.Calculcator = calculator;
+        this.Partition = partition;
+        this.IgnoreMissingValues = ignoreMissingValues;
+        this.Variable = variable;
+      }
+    }
+
+    public delegate void CorrelationCalculationFinishedHandler(object sender, CorrelationCalculationFinishedArgs e);
+    public event CorrelationCalculationFinishedHandler CorrelationCalculationFinished;
+    protected virtual void OnCorrelationCalculationFinished(double[,] correlation, IDependencyCalculator calculator, string partition, bool ignoreMissingValues, string variable = null) {
+      var handler = CorrelationCalculationFinished;
+      if (handler != null)
+        handler(this, new CorrelationCalculationFinishedArgs(correlation, calculator, partition, ignoreMissingValues, variable));
+    }
+
+    public event ProgressChangedEventHandler ProgressChanged;
+    protected virtual void BackgroundWorker_ProgressChanged(object sender, ProgressChangedEventArgs e) {
+      var handler = ProgressChanged;
+      if (handler != null) {
+        handler(sender, e);
+      }
+    }
+    #endregion
+
+    protected class BackgroundWorkerInfo {
+      public IDataset Dataset { get; set; }
+      public IDependencyCalculator Calculator { get; set; }
+      public string Partition { get; set; }
+      public IEnumerable<int> Indices { get; set; }
+
+      public bool IgnoreMissingValues { get; set; }
+
+      public string Variable { get; set; }
+      public int Frames { get; set; }
+      public double[,] AlreadyCalculated { get; set; }
+    }
+  }
+}
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/AbstractFeatureCorrelationView.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/AbstractFeatureCorrelationView.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/AbstractFeatureCorrelationView.cs	(revision 13938)
@@ -37,7 +37,7 @@
     public const string TESTSAMPLES = "Test Samples";
 
-    public static readonly IList<string> Partitions = new List<string>() { ALLSAMPLES, TRAININGSAMPLES, TESTSAMPLES };
+    public static readonly IList<string> Partitions = new List<string>() { ALLSAMPLES, TRAININGSAMPLES, TESTSAMPLES }.AsReadOnly();
 
-    protected FeatureCorrelationCalculator fcc;
+    protected AbstractFeatureCorrelationCalculator CorrelationCalculator { get; set; }
 
     public new DataAnalysisProblemData Content {
@@ -49,5 +49,4 @@
       InitializeComponent();
       dataView.FormatPattern = "0.000";
-      fcc = new FeatureCorrelationCalculator();
       var calculators = ApplicationManager.Manager.GetInstances<IDependencyCalculator>();
       var calcList = calculators.OrderBy(c => c.Name).Select(c => new { Name = c.Name, Calculator = c }).ToList();
@@ -55,5 +54,5 @@
       correlationCalcComboBox.DisplayMember = "Name";
       correlationCalcComboBox.DataSource = calcList;
-      correlationCalcComboBox.SelectedItem = calcList.First(c => c.Calculator.GetType().Equals(typeof(PearsonsRDependenceCalculator)));
+      correlationCalcComboBox.SelectedItem = calcList.First(c => c.Calculator.GetType() == typeof(PearsonsRDependenceCalculator));
       partitionComboBox.DataSource = Partitions;
       partitionComboBox.SelectedItem = TRAININGSAMPLES;
@@ -61,13 +60,18 @@
     }
 
+    protected override void OnClosing(FormClosingEventArgs e) {
+      base.OnClosing(e);
+      CorrelationCalculator.TryCancelCalculation();
+    }
+
     protected override void RegisterContentEvents() {
       base.RegisterContentEvents();
-      fcc.ProgressCalculation += new FeatureCorrelationCalculator.ProgressCalculationHandler(Content_ProgressCalculation);
-      fcc.CorrelationCalculationFinished += new FeatureCorrelationCalculator.CorrelationCalculationFinishedHandler(Content_CorrelationCalculationFinished);
+      CorrelationCalculator.ProgressChanged += FeatureCorrelation_ProgressChanged;
+      CorrelationCalculator.CorrelationCalculationFinished += FeatureCorrelation_CalculationFinished;
     }
 
     protected override void DeregisterContentEvents() {
-      fcc.CorrelationCalculationFinished -= new FeatureCorrelationCalculator.CorrelationCalculationFinishedHandler(Content_CorrelationCalculationFinished);
-      fcc.ProgressCalculation -= new FeatureCorrelationCalculator.ProgressCalculationHandler(Content_ProgressCalculation);
+      CorrelationCalculator.ProgressChanged -= FeatureCorrelation_ProgressChanged;
+      CorrelationCalculator.CorrelationCalculationFinished -= FeatureCorrelation_CalculationFinished;
       base.DeregisterContentEvents();
     }
@@ -75,7 +79,6 @@
     protected override void OnContentChanged() {
       base.OnContentChanged();
-      fcc.TryCancelCalculation();
+      CorrelationCalculator.TryCancelCalculation();
       if (Content != null) {
-        fcc.ProblemData = Content;
         CalculateCorrelation();
       } else {
@@ -106,5 +109,7 @@
 
     protected abstract void CalculateCorrelation();
-    protected abstract void Content_CorrelationCalculationFinished(object sender, FeatureCorrelationCalculator.CorrelationCalculationFinishedArgs e);
+
+    protected abstract void FeatureCorrelation_CalculationFinished(object sender,
+      AbstractFeatureCorrelationCalculator.CorrelationCalculationFinishedArgs e);
 
     protected void UpdateDataView(DoubleMatrix correlation) {
@@ -121,5 +126,5 @@
     }
 
-    protected void Content_ProgressCalculation(object sender, ProgressChangedEventArgs e) {
+    protected void FeatureCorrelation_ProgressChanged(object sender, ProgressChangedEventArgs e) {
       if (!progressPanel.Visible && e.ProgressPercentage != progressBar.Maximum) {
         progressPanel.Show();
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationCalculator.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationCalculator.cs	(revision 13938)
@@ -24,99 +24,27 @@
 using System.ComponentModel;
 using System.Linq;
+using System.Threading.Tasks;
 using HeuristicLab.PluginInfrastructure;
 
 namespace HeuristicLab.Problems.DataAnalysis.Views {
   [NonDiscoverableType]
-  public class FeatureCorrelationCalculator : Object {
+  public sealed class FeatureCorrelationCalculator : AbstractFeatureCorrelationCalculator {
+    public FeatureCorrelationCalculator() : base() { }
 
-    private BackgroundWorker bw;
-    private BackgroundWorkerInfo bwInfo;
+    public void CalculateElements(IDataAnalysisProblemData problemData, IDependencyCalculator calc, string partition, bool ignoreMissingValues) {
+      var indices = GetRelevantIndices(problemData, partition);
+      var info = new BackgroundWorkerInfo {
+        Dataset = problemData.Dataset, Calculator = calc, Partition = partition, Indices = indices, IgnoreMissingValues = ignoreMissingValues
+      };
 
-    private IDataAnalysisProblemData problemData;
-    public IDataAnalysisProblemData ProblemData {
-      set {
-        if (bw != null) {
-          bw.CancelAsync();
-        }
-        problemData = value;
-      }
+      StartCalculation(info);
     }
 
-    public FeatureCorrelationCalculator()
-      : base() { }
+    protected override void BackgroundWorker_DoWork(object sender, DoWorkEventArgs e) {
+      BackgroundWorker worker = (BackgroundWorker)sender;
+      BackgroundWorkerInfo bwInfo = (BackgroundWorkerInfo)e.Argument;
 
-    public FeatureCorrelationCalculator(IDataAnalysisProblemData problemData)
-      : base() {
-      this.problemData = problemData;
-    }
-
-    public void CalculateElements(IDependencyCalculator calc, string partition) {
-      CalculateElements(problemData.Dataset, calc, partition);
-    }
-
-    // returns true if any calculation takes place
-    public bool CalculateTimeframeElements(IDependencyCalculator calc, string partition, string variable, int frames, double[,] correlation = null) {
-      if (correlation == null || correlation.GetLength(1) <= frames) {
-        CalculateElements(problemData.Dataset, calc, partition, variable, frames, correlation);
-        return true;
-      } else {
-        return false;
-      }
-    }
-
-    public void TryCancelCalculation() {
-      if (bw != null && bw.IsBusy) {
-        bwInfo = null;
-        bw.CancelAsync();
-      }
-    }
-
-    private void CalculateElements(IDataset dataset, IDependencyCalculator calc, string partition, string variable = null, int frames = 0, double[,] alreadyCalculated = null) {
-      var indices = GetRelevantIndices(problemData, partition);
-      bwInfo = new BackgroundWorkerInfo {
-        Dataset = dataset, Calculator = calc, Partition = partition, Indices = indices,
-        Variable = variable, Frames = frames, AlreadyCalculated = alreadyCalculated
-      };
-      if (bw == null) {
-        bw = new BackgroundWorker();
-        bw.WorkerReportsProgress = true;
-        bw.WorkerSupportsCancellation = true;
-        bw.DoWork += new DoWorkEventHandler(BwDoWork);
-        bw.ProgressChanged += new ProgressChangedEventHandler(BwProgressChanged);
-        bw.RunWorkerCompleted += new RunWorkerCompletedEventHandler(BwRunWorkerCompleted);
-      }
-      if (bw.IsBusy) {
-        bw.CancelAsync();
-      } else {
-        bw.RunWorkerAsync(bwInfo);
-      }
-    }
-
-    private IEnumerable<int> GetRelevantIndices(IDataAnalysisProblemData problemData, string partition) {
-      IEnumerable<int> var;
-      if (partition.Equals(AbstractFeatureCorrelationView.TRAININGSAMPLES))
-        var = problemData.TrainingIndices;
-      else if (partition.Equals(AbstractFeatureCorrelationView.TESTSAMPLES))
-        var = problemData.TestIndices;
-      else var = Enumerable.Range(0, problemData.Dataset.Rows);
-      return var;
-    }
-
-    #region backgroundworker
-    private void BwDoWork(object sender, DoWorkEventArgs e) {
-      BackgroundWorkerInfo bwInfo = (BackgroundWorkerInfo)e.Argument;
-      if (bwInfo.Variable == null) {
-        BwCalculateCorrelation(sender, e);
-      } else {
-        BwCalculateTimeframeCorrelation(sender, e);
-      }
-    }
-
-    private void BwCalculateCorrelation(object sender, DoWorkEventArgs e) {
-      BackgroundWorker worker = sender as BackgroundWorker;
-
-      BackgroundWorkerInfo bwInfo = (BackgroundWorkerInfo)e.Argument;
       var dataset = bwInfo.Dataset;
-      IEnumerable<int> indices = bwInfo.Indices;
+      var indices = bwInfo.Indices.ToArray();
       IDependencyCalculator calc = bwInfo.Calculator;
 
@@ -125,19 +53,24 @@
       int length = doubleVariableNames.Count;
       double[,] elements = new double[length, length];
-      double calculations = (Math.Pow(length, 2) + length) / 2;
 
       worker.ReportProgress(0);
 
-      for (int i = 0; i < length; i++) {
-        for (int j = 0; j < i + 1; j++) {
-          if (worker.CancellationPending) {
-            worker.ReportProgress(100);
-            e.Cancel = true;
-            return;
-          }
-          IEnumerable<double> var1 = problemData.Dataset.GetDoubleValues(doubleVariableNames[i], indices);
-          IEnumerable<double> var2 = problemData.Dataset.GetDoubleValues(doubleVariableNames[j], indices);
+      for (int counter = 0; counter < length; counter++) {
+        if (worker.CancellationPending) {
+          worker.ReportProgress(100);
+          e.Cancel = true;
+          return;
+        }
 
-          elements[i, j] = calc.Calculate(var1, var2, out error);
+        var i = counter;
+        Parallel.ForEach(Enumerable.Range(i, length - i), j => {
+          var var1 = dataset.GetDoubleValues(doubleVariableNames[i], indices);
+          var var2 = dataset.GetDoubleValues(doubleVariableNames[j], indices);
+
+          if (bwInfo.IgnoreMissingValues) {
+            var filtered = FilterNaNValues(var1, var2);
+            elements[i, j] = calc.Calculate(filtered, out error);
+          } else
+            elements[i, j] = calc.Calculate(var1, var2, out error);
 
           if (!error.Equals(OnlineCalculatorError.None)) {
@@ -145,6 +78,7 @@
           }
           elements[j, i] = elements[i, j];
-          worker.ReportProgress((int)Math.Round((((Math.Pow(i, 2) + i) / 2 + j + 1.0) / calculations) * 100));
-        }
+
+        });
+        worker.ReportProgress((int)(((double)counter) / length * 100));
       }
       e.Result = elements;
@@ -152,114 +86,22 @@
     }
 
-    private void BwCalculateTimeframeCorrelation(object sender, DoWorkEventArgs e) {
-      BackgroundWorker worker = sender as BackgroundWorker;
 
-      BackgroundWorkerInfo bwInfo = (BackgroundWorkerInfo)e.Argument;
-      var dataset = bwInfo.Dataset;
-      IEnumerable<int> indices = bwInfo.Indices;
-      IDependencyCalculator calc = bwInfo.Calculator;
-      string variable = bwInfo.Variable;
-      int frames = bwInfo.Frames;
-      double[,] alreadyCalculated = bwInfo.AlreadyCalculated;
+    private static IEnumerable<Tuple<double, double>> FilterNaNValues(IEnumerable<double> first, IEnumerable<double> second) {
+      var firstEnumerator = first.GetEnumerator();
+      var secondEnumerator = second.GetEnumerator();
 
-      IList<string> doubleVariableNames = dataset.DoubleVariables.ToList();
-      OnlineCalculatorError error = OnlineCalculatorError.None;
-      int length = doubleVariableNames.Count;
-      double[,] elements = new double[length, frames + 1];
-      double calculations = (frames + 1) * length;
+      while (firstEnumerator.MoveNext() & secondEnumerator.MoveNext()) {
+        var firstValue = firstEnumerator.Current;
+        var secondValue = secondEnumerator.Current;
 
-      worker.ReportProgress(0);
+        if (double.IsNaN(firstValue)) continue;
+        if (double.IsNaN(secondValue)) continue;
 
-      int start = 0;
-      if (alreadyCalculated != null) {
-        for (int i = 0; i < alreadyCalculated.GetLength(0); i++) {
-          Array.Copy(alreadyCalculated, i * alreadyCalculated.GetLength(1), elements, i * elements.GetLength(1), alreadyCalculated.GetLength(1));
-        }
-        start = alreadyCalculated.GetLength(1);
+        yield return Tuple.Create(firstValue, secondValue);
       }
 
-      for (int i = 0; i < length; i++) {
-        for (int j = start; j <= frames; j++) {
-          if (worker.CancellationPending) {
-            worker.ReportProgress(100);
-            e.Cancel = true;
-            return;
-          }
-
-          IEnumerable<double> var1 = problemData.Dataset.GetDoubleValues(variable, indices);
-          IEnumerable<double> var2 = problemData.Dataset.GetDoubleValues(doubleVariableNames[i], indices);
-
-          var valuesInFrame = var1.Take(j);
-          var help = var1.Skip(j).ToList();
-          help.AddRange(valuesInFrame);
-          var1 = help;
-
-          elements[i, j] = calc.Calculate(var1, var2, out error);
-
-          if (!error.Equals(OnlineCalculatorError.None)) {
-            elements[i, j] = double.NaN;
-          }
-          worker.ReportProgress((int)((100.0 / calculations) * (i * (frames + 1) + j + 1)));
-        }
+      if (firstEnumerator.MoveNext() || secondEnumerator.MoveNext()) {
+        throw new ArgumentException("Number of elements in first and second enumeration doesn't match.");
       }
-      e.Result = elements;
-      worker.ReportProgress(100);
-    }
-
-    private void BwRunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e) {
-      BackgroundWorker worker = sender as BackgroundWorker;
-      if (!e.Cancelled && !worker.CancellationPending) {
-        if (e.Error != null) {
-          ErrorHandling.ShowErrorDialog(e.Error);
-        } else {
-          OnCorrelationCalculationFinished((double[,])e.Result, bwInfo.Calculator, bwInfo.Partition, bwInfo.Variable);
-        }
-      } else if (bwInfo != null) {
-        bw.RunWorkerAsync(bwInfo);
-      }
-    }
-    #endregion
-
-    #region events
-    public class CorrelationCalculationFinishedArgs : EventArgs {
-      public double[,] Correlation { get; private set; }
-      public IDependencyCalculator Calculcator { get; private set; }
-      public string Partition { get; private set; }
-      public string Variable { get; private set; }
-
-      public CorrelationCalculationFinishedArgs(double[,] correlation, IDependencyCalculator calculator, string partition, string variable = null) {
-        this.Correlation = correlation;
-        this.Calculcator = calculator;
-        this.Partition = partition;
-        this.Variable = variable;
-      }
-    }
-
-    public delegate void CorrelationCalculationFinishedHandler(object sender, CorrelationCalculationFinishedArgs e);
-    public event CorrelationCalculationFinishedHandler CorrelationCalculationFinished;
-    protected virtual void OnCorrelationCalculationFinished(double[,] correlation, IDependencyCalculator calculator, string partition, string variable = null) {
-      var handler = CorrelationCalculationFinished;
-      if (handler != null)
-        handler(this, new CorrelationCalculationFinishedArgs(correlation, calculator, partition, variable));
-    }
-
-    public delegate void ProgressCalculationHandler(object sender, ProgressChangedEventArgs e);
-    public event ProgressCalculationHandler ProgressCalculation;
-    protected void BwProgressChanged(object sender, ProgressChangedEventArgs e) {
-      BackgroundWorker worker = sender as BackgroundWorker;
-      if (ProgressCalculation != null) {
-        ProgressCalculation(sender, e);
-      }
-    }
-    #endregion
-
-    private class BackgroundWorkerInfo {
-      public IDataset Dataset { get; set; }
-      public IDependencyCalculator Calculator { get; set; }
-      public string Partition { get; set; }
-      public IEnumerable<int> Indices { get; set; }
-      public string Variable { get; set; }
-      public int Frames { get; set; }
-      public double[,] AlreadyCalculated { get; set; }
     }
   }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationView.Designer.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationView.Designer.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationView.Designer.cs	(revision 13938)
@@ -47,5 +47,49 @@
     /// </summary>
     private void InitializeComponent() {
+      this.ignoreMissingValuesCheckbox = new System.Windows.Forms.CheckBox();
+      ((System.ComponentModel.ISupportInitialize)(this.pictureBox)).BeginInit();
+      ((System.ComponentModel.ISupportInitialize)(this.splitContainer)).BeginInit();
+      this.splitContainer.Panel1.SuspendLayout();
+      this.splitContainer.Panel2.SuspendLayout();
+      this.splitContainer.SuspendLayout();
+      this.progressPanel.SuspendLayout();
       this.SuspendLayout();
+      // 
+      // minimumLabel
+      // 
+      this.minimumLabel.Location = new System.Drawing.Point(707, 434);
+      // 
+      // maximumLabel
+      // 
+      this.maximumLabel.Location = new System.Drawing.Point(707, 2);
+      // 
+      // pictureBox
+      // 
+      this.pictureBox.Location = new System.Drawing.Point(727, 30);
+      this.pictureBox.Size = new System.Drawing.Size(35, 401);
+      // 
+      // splitContainer
+      // 
+      // 
+      // splitContainer.Panel1
+      // 
+      this.splitContainer.Panel1.Controls.Add(this.ignoreMissingValuesCheckbox);
+      this.splitContainer.Size = new System.Drawing.Size(695, 450);
+      // 
+      // dataView
+      // 
+      this.dataView.Size = new System.Drawing.Size(695, 421);
+      // 
+      // ignoreMissingValuesCheckbox
+      // 
+      this.ignoreMissingValuesCheckbox.AutoSize = true;
+      this.ignoreMissingValuesCheckbox.CheckAlign = System.Drawing.ContentAlignment.MiddleRight;
+      this.ignoreMissingValuesCheckbox.Location = new System.Drawing.Point(481, 6);
+      this.ignoreMissingValuesCheckbox.Name = "ignoreMissingValuesCheckbox";
+      this.ignoreMissingValuesCheckbox.Size = new System.Drawing.Size(122, 17);
+      this.ignoreMissingValuesCheckbox.TabIndex = 11;
+      this.ignoreMissingValuesCheckbox.Text = "ignoreMissingValues";
+      this.ignoreMissingValuesCheckbox.UseVisualStyleBackColor = true;
+      this.ignoreMissingValuesCheckbox.CheckedChanged += new System.EventHandler(this.ignoreMissingValuesCheckbox_CheckedChanged);
       // 
       // FeatureCorrelationView
@@ -54,8 +98,19 @@
       this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
       this.Name = "FeatureCorrelationView";
-      this.Size = new System.Drawing.Size(569, 336);
+      this.Size = new System.Drawing.Size(789, 456);
+      ((System.ComponentModel.ISupportInitialize)(this.pictureBox)).EndInit();
+      this.splitContainer.Panel1.ResumeLayout(false);
+      this.splitContainer.Panel1.PerformLayout();
+      this.splitContainer.Panel2.ResumeLayout(false);
+      ((System.ComponentModel.ISupportInitialize)(this.splitContainer)).EndInit();
+      this.splitContainer.ResumeLayout(false);
+      this.progressPanel.ResumeLayout(false);
+      this.progressPanel.PerformLayout();
       this.ResumeLayout(false);
+
     }
     #endregion
+
+    private System.Windows.Forms.CheckBox ignoreMissingValuesCheckbox;
   }
 }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationView.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationView.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/FeatureCorrelationView.cs	(revision 13938)
@@ -34,8 +34,13 @@
 
     private FeatureCorrelationCache correlationCache;
+    private new FeatureCorrelationCalculator CorrelationCalculator {
+      get { return (FeatureCorrelationCalculator)base.CorrelationCalculator; }
+      set { base.CorrelationCalculator = value; }
+    }
 
     public FeatureCorrelationView()
       : base() {
       InitializeComponent();
+      CorrelationCalculator = new FeatureCorrelationCalculator();
       correlationCache = new FeatureCorrelationCache();
     }
@@ -49,4 +54,8 @@
     }
 
+    private void ignoreMissingValuesCheckbox_CheckedChanged(object sender, EventArgs e) {
+      CalculateCorrelation();
+    }
+
     protected override void CalculateCorrelation() {
       if (correlationCalcComboBox.SelectedItem == null) return;
@@ -56,9 +65,9 @@
       string partition = (string)partitionComboBox.SelectedValue;
       dataView.Enabled = false;
-      double[,] corr = correlationCache.GetCorrelation(calc, partition);
+      double[,] corr = correlationCache.GetCorrelation(calc, partition, ignoreMissingValuesCheckbox.Checked);
       if (corr == null) {
-        fcc.CalculateElements(calc, partition);
+        CorrelationCalculator.CalculateElements(Content, calc, partition, ignoreMissingValuesCheckbox.Checked);
       } else {
-        fcc.TryCancelCalculation();
+        CorrelationCalculator.TryCancelCalculation();
         var correlation = new DoubleMatrix(corr, Content.Dataset.DoubleVariables, Content.Dataset.DoubleVariables);
         UpdateDataView(correlation);
@@ -66,12 +75,11 @@
     }
 
-
-
-    protected override void Content_CorrelationCalculationFinished(object sender, FeatureCorrelationCalculator.CorrelationCalculationFinishedArgs e) {
+    protected override void FeatureCorrelation_CalculationFinished(object sender, AbstractFeatureCorrelationCalculator.CorrelationCalculationFinishedArgs e) {
       if (InvokeRequired) {
-        Invoke(new FeatureCorrelationCalculator.CorrelationCalculationFinishedHandler(Content_CorrelationCalculationFinished), sender, e);
+        Invoke(new AbstractFeatureCorrelationCalculator.CorrelationCalculationFinishedHandler(FeatureCorrelation_CalculationFinished), sender, e);
         return;
       }
-      correlationCache.SetCorrelation(e.Calculcator, e.Partition, e.Correlation);
+      correlationCache.SetCorrelation(e.Calculcator, e.Partition, e.IgnoreMissingValues, e.Correlation);
+
       var correlation = new DoubleMatrix(e.Correlation, Content.Dataset.DoubleVariables, Content.Dataset.DoubleVariables);
       UpdateDataView(correlation);
@@ -80,5 +88,5 @@
     [NonDiscoverableType]
     private class FeatureCorrelationCache : Object {
-      private Dictionary<Tuple<IDependencyCalculator, string>, double[,]> correlationsCache;
+      private Dictionary<Tuple<IDependencyCalculator, string, bool>, double[,]> correlationsCache;
 
       public FeatureCorrelationCache()
@@ -88,5 +96,5 @@
 
       private void InitializeCaches() {
-        correlationsCache = new Dictionary<Tuple<IDependencyCalculator, string>, double[,]>();
+        correlationsCache = new Dictionary<Tuple<IDependencyCalculator, string, bool>, double[,]>();
       }
 
@@ -95,13 +103,13 @@
       }
 
-      public double[,] GetCorrelation(IDependencyCalculator calc, string partition) {
+      public double[,] GetCorrelation(IDependencyCalculator calc, string partition, bool ignoreMissingValues) {
         double[,] corr;
-        var key = new Tuple<IDependencyCalculator, string>(calc, partition);
+        var key = Tuple.Create(calc, partition, ignoreMissingValues);
         correlationsCache.TryGetValue(key, out corr);
         return corr;
       }
 
-      public void SetCorrelation(IDependencyCalculator calc, string partition, double[,] correlation) {
-        var key = new Tuple<IDependencyCalculator, string>(calc, partition);
+      public void SetCorrelation(IDependencyCalculator calc, string partition, bool ignoreMissingValues, double[,] correlation) {
+        var key = Tuple.Create(calc, partition, ignoreMissingValues);
         correlationsCache[key] = correlation;
       }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/TimeframeFeatureCorrelationCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/TimeframeFeatureCorrelationCalculator.cs	(revision 13938)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/TimeframeFeatureCorrelationCalculator.cs	(revision 13938)
@@ -0,0 +1,103 @@
+﻿#region License Information
+
+/* HeuristicLab
+ * Copyright (C) 2002-2016 Heuristic and Evolutionary Algorithms Laboratory (HEAL)
+ *
+ * This file is part of HeuristicLab.
+ *
+ * HeuristicLab 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.
+ *
+ * HeuristicLab 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 HeuristicLab. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+#endregion
+
+using System;
+using System.Collections.Generic;
+using System.ComponentModel;
+using System.Linq;
+using HeuristicLab.PluginInfrastructure;
+
+namespace HeuristicLab.Problems.DataAnalysis.Views {
+  [NonDiscoverableType]
+  public class TimeframeFeatureCorrelationCalculator : AbstractFeatureCorrelationCalculator {
+    public TimeframeFeatureCorrelationCalculator() : base() { }
+
+    // returns true if any calculation takes place
+    public bool CalculateTimeframeElements(IDataAnalysisProblemData problemData, IDependencyCalculator calc, string partition, string variable, int frames, double[,] correlation = null) {
+      if (correlation != null && correlation.GetLength(1) > frames) return false;
+
+      var indices = GetRelevantIndices(problemData, partition);
+      var info = new BackgroundWorkerInfo {
+        Dataset = problemData.Dataset, Calculator = calc, Partition = partition, Indices = indices, Variable = variable, Frames = frames, AlreadyCalculated = correlation
+      };
+
+      StartCalculation(info);
+      return true;
+    }
+
+    protected override void BackgroundWorker_DoWork(object sender, DoWorkEventArgs e) {
+      BackgroundWorker worker = (BackgroundWorker)sender;
+      BackgroundWorkerInfo bwInfo = (BackgroundWorkerInfo)e.Argument;
+
+      var dataset = bwInfo.Dataset;
+      var indices = bwInfo.Indices.ToArray();
+      IDependencyCalculator calc = bwInfo.Calculator;
+      string variable = bwInfo.Variable;
+      int frames = bwInfo.Frames;
+      double[,] alreadyCalculated = bwInfo.AlreadyCalculated;
+
+      IList<string> doubleVariableNames = dataset.DoubleVariables.ToList();
+      int length = doubleVariableNames.Count;
+      double[,] elements = new double[length, frames + 1];
+      double calculations = (frames + 1) * length;
+
+      worker.ReportProgress(0);
+
+      int start = 0;
+      if (alreadyCalculated != null) {
+        for (int i = 0; i < alreadyCalculated.GetLength(0); i++) {
+          Array.Copy(alreadyCalculated, i * alreadyCalculated.GetLength(1), elements, i * elements.GetLength(1), alreadyCalculated.GetLength(1));
+        }
+        start = alreadyCalculated.GetLength(1);
+      }
+
+      for (int i = 0; i < length; i++) {
+        for (int j = start; j <= frames; j++) {
+          if (worker.CancellationPending) {
+            worker.ReportProgress(100);
+            e.Cancel = true;
+            return;
+          }
+
+          IEnumerable<double> var1 = dataset.GetDoubleValues(variable, indices);
+          IEnumerable<double> var2 = dataset.GetDoubleValues(doubleVariableNames[i], indices);
+
+          var valuesInFrame = var1.Take(j);
+          var help = var1.Skip(j).ToList();
+          help.AddRange(valuesInFrame);
+          var1 = help;
+
+          var error = OnlineCalculatorError.None;
+          elements[i, j] = calc.Calculate(var1, var2, out error);
+
+          if (!error.Equals(OnlineCalculatorError.None)) {
+            elements[i, j] = double.NaN;
+          }
+          worker.ReportProgress((int)((100.0 / calculations) * (i * (frames + 1) + j + 1)));
+        }
+      }
+      e.Result = elements;
+      worker.ReportProgress(100);
+    }
+  }
+}
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/TimeframeFeatureCorrelationView.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/TimeframeFeatureCorrelationView.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/FeatureCorrelation/TimeframeFeatureCorrelationView.cs	(revision 13938)
@@ -36,6 +36,13 @@
     private string lastFramesValue;
 
+    private new TimeframeFeatureCorrelationCalculator CorrelationCalculator {
+      get { return (TimeframeFeatureCorrelationCalculator)base.CorrelationCalculator; }
+      set { base.CorrelationCalculator = value; }
+    }
+
+
     public TimeframeFeatureCorrelationView() {
       InitializeComponent();
+      CorrelationCalculator = new TimeframeFeatureCorrelationCalculator();
       correlationTimeframCache = new FeatureCorrelationTimeframeCache();
       errorProvider.SetIconAlignment(timeframeTextbox, ErrorIconAlignment.MiddleRight);
@@ -93,30 +100,31 @@
 
     protected override void CalculateCorrelation() {
-      if (correlationCalcComboBox.SelectedItem != null && partitionComboBox.SelectedItem != null
-        && variableSelectionComboBox.SelectedItem != null) {
-        string variable = (string)variableSelectionComboBox.SelectedItem;
-        IDependencyCalculator calc = (IDependencyCalculator)correlationCalcComboBox.SelectedValue;
-        string partition = (string)partitionComboBox.SelectedValue;
-        int frames;
-        int.TryParse(timeframeTextbox.Text, out frames);
-        dataView.Enabled = false;
-        double[,] corr = correlationTimeframCache.GetTimeframeCorrelation(calc, partition, variable);
-        if (corr == null) {
-          fcc.CalculateTimeframeElements(calc, partition, variable, frames);
-        } else if (corr.GetLength(1) <= frames) {
-          fcc.CalculateTimeframeElements(calc, partition, variable, frames, corr);
-        } else {
-          fcc.TryCancelCalculation();
-          var columnNames = Enumerable.Range(0, corr.GetLength(1)).Select(x => x.ToString());
-          var correlation = new DoubleMatrix(corr, columnNames, Content.Dataset.DoubleVariables);
-          ((IStringConvertibleMatrix)correlation).Columns = frames + 1;
-          UpdateDataView(correlation);
-        }
+      if (correlationCalcComboBox.SelectedItem == null) return;
+      if (partitionComboBox.SelectedItem == null) return;
+      if (variableSelectionComboBox.SelectedItem == null) return;
+
+      string variable = (string)variableSelectionComboBox.SelectedItem;
+      IDependencyCalculator calc = (IDependencyCalculator)correlationCalcComboBox.SelectedValue;
+      string partition = (string)partitionComboBox.SelectedValue;
+      int frames;
+      int.TryParse(timeframeTextbox.Text, out frames);
+      dataView.Enabled = false;
+      double[,] corr = correlationTimeframCache.GetTimeframeCorrelation(calc, partition, variable);
+      if (corr == null) {
+        CorrelationCalculator.CalculateTimeframeElements(Content, calc, partition, variable, frames);
+      } else if (corr.GetLength(1) <= frames) {
+        CorrelationCalculator.CalculateTimeframeElements(Content, calc, partition, variable, frames, corr);
+      } else {
+        CorrelationCalculator.TryCancelCalculation();
+        var columnNames = Enumerable.Range(0, corr.GetLength(1)).Select(x => x.ToString());
+        var correlation = new DoubleMatrix(corr, columnNames, Content.Dataset.DoubleVariables);
+        ((IStringConvertibleMatrix)correlation).Columns = frames + 1;
+        UpdateDataView(correlation);
       }
     }
 
-    protected override void Content_CorrelationCalculationFinished(object sender, FeatureCorrelationCalculator.CorrelationCalculationFinishedArgs e) {
+    protected override void FeatureCorrelation_CalculationFinished(object sender, AbstractFeatureCorrelationCalculator.CorrelationCalculationFinishedArgs e) {
       if (InvokeRequired) {
-        Invoke(new FeatureCorrelationCalculator.CorrelationCalculationFinishedHandler(Content_CorrelationCalculationFinished), sender, e);
+        Invoke(new AbstractFeatureCorrelationCalculator.CorrelationCalculationFinishedHandler(FeatureCorrelation_CalculationFinished), sender, e);
       } else {
         correlationTimeframCache.SetTimeframeCorrelation(e.Calculcator, e.Partition, e.Variable, e.Correlation);
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/HeuristicLab.Problems.DataAnalysis.Views-3.4.csproj
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/HeuristicLab.Problems.DataAnalysis.Views-3.4.csproj	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis.Views/3.4/HeuristicLab.Problems.DataAnalysis.Views-3.4.csproj	(revision 13938)
@@ -120,4 +120,6 @@
   </ItemGroup>
   <ItemGroup>
+    <Compile Include="FeatureCorrelation\TimeframeFeatureCorrelationCalculator.cs" />
+    <Compile Include="FeatureCorrelation\AbstractFeatureCorrelationCalculator.cs" />
     <Compile Include="Classification\ClassificationEnsembleSolutionEstimatedClassValuesView.cs">
       <SubType>UserControl</SubType>
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/IDependencyCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/IDependencyCalculator.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/Interfaces/IDependencyCalculator.cs	(revision 13938)
@@ -20,4 +20,5 @@
 #endregion
 
+using System;
 using System.Collections.Generic;
 
@@ -29,4 +30,5 @@
 
     double Calculate(IEnumerable<double> originalValues, IEnumerable<double> estimatedValues, out OnlineCalculatorError errorState);
+    double Calculate(IEnumerable<Tuple<double, double>> values, out OnlineCalculatorError errorState);
   }
 }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/HoeffdingsDependenceCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/HoeffdingsDependenceCalculator.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/HoeffdingsDependenceCalculator.cs	(revision 13938)
@@ -41,4 +41,8 @@
       if (errorState != OnlineCalculatorError.None) return double.NaN;
       return d;
+    }
+
+    public double Calculate(IEnumerable<Tuple<double, double>> values, out OnlineCalculatorError errorState) {
+      return HoeffD(values.Select(v => v.Item1), values.Select(v => v.Item2), out errorState);
     }
 
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/PearsonsRDependenceCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/PearsonsRDependenceCalculator.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/PearsonsRDependenceCalculator.cs	(revision 13938)
@@ -35,4 +35,14 @@
       return OnlinePearsonsRCalculator.Calculate(originalValues, estimatedValues, out errorState);
     }
+
+    public double Calculate(IEnumerable<Tuple<double, double>> values, out OnlineCalculatorError errorState) {
+      var calculator = new OnlinePearsonsRCalculator();
+      foreach (var tuple in values) {
+        calculator.Add(tuple.Item1, tuple.Item2);
+        if (calculator.ErrorState != OnlineCalculatorError.None) break;
+      }
+      errorState = calculator.ErrorState;
+      return calculator.R;
+    }
   }
 }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/PearsonsRSquaredDependenceCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/PearsonsRSquaredDependenceCalculator.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/PearsonsRSquaredDependenceCalculator.cs	(revision 13938)
@@ -20,4 +20,5 @@
 #endregion
 
+using System;
 using System.Collections.Generic;
 
@@ -35,4 +36,15 @@
       return r * r;
     }
+
+    public double Calculate(IEnumerable<Tuple<double, double>> values, out OnlineCalculatorError errorState) {
+      var calculator = new OnlinePearsonsRCalculator();
+      foreach (var tuple in values) {
+        calculator.Add(tuple.Item1, tuple.Item2);
+        if (calculator.ErrorState != OnlineCalculatorError.None) break;
+      }
+      errorState = calculator.ErrorState;
+      var r = calculator.R;
+      return r * r;
+    }
   }
 }
Index: trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/SpearmansRankCorrelationCoefficientCalculator.cs
===================================================================
--- trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/SpearmansRankCorrelationCoefficientCalculator.cs	(revision 13935)
+++ trunk/sources/HeuristicLab.Problems.DataAnalysis/3.4/OnlineCalculators/DependencyCalculator/SpearmansRankCorrelationCoefficientCalculator.cs	(revision 13938)
@@ -20,4 +20,5 @@
 #endregion
 
+using System;
 using System.Collections.Generic;
 using System.Linq;
@@ -33,5 +34,8 @@
 
     public double Calculate(IEnumerable<double> originalValues, IEnumerable<double> estimatedValues, out OnlineCalculatorError errorState) {
-      return SpearmansRankCorrelationCoefficientCalculator.CalculateSpearmansRank(originalValues, estimatedValues, out errorState);
+      return CalculateSpearmansRank(originalValues, estimatedValues, out errorState);
+    }
+    public double Calculate(IEnumerable<Tuple<double, double>> values, out OnlineCalculatorError errorState) {
+      return CalculateSpearmansRank(values.Select(v => v.Item1), values.Select(v => v.Item2), out errorState);
     }
 
@@ -50,4 +54,6 @@
       return rs;
     }
+
+
   }
 }
