/// <summary> /// Evaluates all given <see cref="ClusterSet{TInstance}" />s according to the given /// <see cref="IInternalEvaluationCriterion{TInstance}" />. /// </summary> /// <param name="clustering">The cluster-sets to be evaluated.</param> /// <param name="criterion">The criterion used to evaluate the cluster-sets.</param> /// <param name="maxClusters">The maximum number of clusters allowed for a cluster-set for it to be evaluated.</param> /// <returns>A list containing the evaluations for each cluster-set.</returns> /// <typeparam name="TInstance">The type of instance considered.</typeparam> public static ICollection <ClusterSetEvaluation <TInstance> > EvaluateClustering <TInstance>( this ClusteringResult <TInstance> clustering, IInternalEvaluationCriterion <TInstance> criterion, uint maxClusters) where TInstance : IComparable <TInstance> { var evals = new List <ClusterSetEvaluation <TInstance> >(); // checks only one cluster allowed if (maxClusters == 1) { evals.Add(new ClusterSetEvaluation <TInstance>(clustering[0], double.NaN)); return(evals); } // evaluates all cluster-sets foreach (var clusterSet in clustering.Reverse()) { if (clusterSet.Count < 2 || clusterSet.Count > maxClusters) { continue; } var eval = criterion.Evaluate(clusterSet); evals.Add(new ClusterSetEvaluation <TInstance>(clusterSet, eval)); } return(evals); }
/// <inheritdoc /> public ClusteringResult <TInstance> GetClustering(IEnumerable <Cluster <TInstance> > clusters, double dissimilarity = 0d) { // initializes elements var currentClusters = clusters.ToArray(); this._clusters = new Cluster <TInstance> [currentClusters.Length * 2 - 1]; this._dissimilarities = new double[currentClusters.Length * 2 - 1][]; this._curClusterCount = 0; // calculates initial dissimilarities foreach (var cluster in currentClusters) { this._clusters[this._curClusterCount] = cluster; this.UpdateDissimilarities(); this._curClusterCount++; } var clustering = new ClusteringResult <TInstance>(currentClusters.Length) { [0] = new ClusterSet <TInstance>(currentClusters, dissimilarity) }; var numSteps = currentClusters.Length; for (var i = 1; i < numSteps; i++) { // gets minimal dissimilarity between a pair of existing clusters var minDissimilarity = this.GetMinDissimilarity(out var clusterIdx1, out var clusterIdx2); // gets a copy of previous clusters, removes new cluster elements var cluster1 = this._clusters[clusterIdx1]; var cluster2 = this._clusters[clusterIdx2]; var newClusters = new Cluster <TInstance> [currentClusters.Length - 1]; var idx = 0; foreach (var cluster in currentClusters) { if (!cluster.Equals(cluster1) && !cluster.Equals(cluster2)) { newClusters[idx++] = cluster; } } this._clusters[clusterIdx1] = null; this._clusters[clusterIdx2] = null; // creates a new cluster from the union of closest clusters (save reference to parents) var newCluster = new Cluster <TInstance>(cluster1, cluster2, minDissimilarity); // adds cluster to list and calculates distance to all others newClusters[idx] = this._clusters[this._curClusterCount] = newCluster; this.UpdateDissimilarities(); this._curClusterCount++; // updates global list of clusters currentClusters = newClusters; clustering[i] = new ClusterSet <TInstance>(currentClusters, minDissimilarity); } this._clusters = null; this._dissimilarities = null; return(clustering); }
/// <summary> /// Evaluates all given <see cref="ClusterSet{TInstance}" />s according to the given /// <see cref="IInternalEvaluationCriterion{TInstance}" />. The maximum number of clusters allowed in a cluster-set for /// it to be evaluated corresponds to sqrt(N/2), where N is the total number of instances clustered. /// </summary> /// <param name="clustering">The cluster-sets to be evaluated.</param> /// <param name="criterion">The criterion used to evaluate the cluster-sets.</param> /// <returns>A list containing the evaluations for each cluster-set.</returns> /// <typeparam name="TInstance">The type of instance considered.</typeparam> public static ICollection <ClusterSetEvaluation <TInstance> > EvaluateClustering <TInstance>( this ClusteringResult <TInstance> clustering, IInternalEvaluationCriterion <TInstance> criterion) where TInstance : IComparable <TInstance> => EvaluateClustering(clustering, criterion, (uint)Math.Sqrt(clustering.Count / 2d));
/// <summary> /// Evaluates all given <see cref="ClusterSet{TInstance}" />s according to the given /// <see cref="IExternalEvaluationCriterion{TInstance,TClass}" />. The maximum number of clusters allowed in a /// cluster-set for it to be evaluated corresponds to sqrt(N/2), where N is the total number of instances clustered. /// </summary> /// <param name="clustering">The cluster-sets to be evaluated.</param> /// <param name="criterion">The criterion used to evaluate the cluster-sets.</param> /// <param name="instanceClasses">The instances' classes.</param> /// <returns>A list containing the evaluations for each cluster-set.</returns> /// <typeparam name="TInstance">The type of instance considered.</typeparam> /// <typeparam name="TClass">The type of class considered.</typeparam> public static ICollection <ClusterSetEvaluation <TInstance> > EvaluateClustering <TInstance, TClass>( this ClusteringResult <TInstance> clustering, IExternalEvaluationCriterion <TInstance, TClass> criterion, IDictionary <TInstance, TClass> instanceClasses) where TInstance : IComparable <TInstance> => EvaluateClustering(clustering, criterion, instanceClasses, (uint)Math.Sqrt(clustering.Count / 2d));