private void evaluateClustersWithRespectToClass(Instances inst, String fileName)
            throws Exception {

        int numClasses = inst.classAttribute().numValues();
        int[][] counts = new int[m_numClusters][numClasses];
        int[] clusterTotals = new int[m_numClusters];
        double[] best = new double[m_numClusters + 1];
        double[] current = new double[m_numClusters + 1];
        DataSource source = null;
        Instances instances = null;
        Instance instance = null;
        int i;
        int numInstances;
         if (fileName == null)
            fileName = "";

        if (fileName.length() != 0) {
            source = new DataSource(fileName);
        } else
            source = new DataSource(inst);
        instances = source.getStructure(inst.classIndex());

        i = 0;
        while (source.hasMoreElements(instances)) {
            instance = source.nextElement(instances);
            if (m_clusterAssignments[i] >= 0) {
                counts[(int) m_clusterAssignments[i]][(int) instance.classValue()]++;
                clusterTotals[(int) m_clusterAssignments[i]]++;
            }
            i++;
        }
        numInstances = i;

        best[m_numClusters] = Double.MAX_VALUE;
        mapClasses(m_numClusters, 0, counts, clusterTotals, current, best, 0);

        m_clusteringResults.append("\n\nClass attribute: "
                + inst.classAttribute().name()
                + "\n");
        m_clusteringResults.append("Classes to Clusters:\n");
        String matrixString = toMatrixString(counts, clusterTotals, new Instances(inst, 0));
        m_clusteringResults.append(matrixString).append("\n");

        int Cwidth = 1 + (int) (Math.log(m_numClusters) / Math.log(10));
        // add the minimum error assignment
        for (i = 0; i < m_numClusters; i++) {
            if (clusterTotals[i] > 0) {
                m_clusteringResults.append("Cluster "
                        + Utils.doubleToString((double) i, Cwidth, 0));
                m_clusteringResults.append(" <-- ");

                if (best[i] < 0) {
                    m_clusteringResults.append("No class\n");
                } else {
                    m_clusteringResults.
                            append(inst.classAttribute().value((int) best[i])).append("\n");
                }
            }
        }
        m_clusteringResults.append("\nIncorrectly clustered instances :\t"
                + best[m_numClusters] + "\t"
                + (Utils.doubleToString((best[m_numClusters] /
                numInstances *
                100.0), 8, 4))
                + " %\n");

        // copy the class assignments
        m_classToCluster = new int[m_numClusters];
        for (i = 0; i < m_numClusters; i++) {
            m_classToCluster[i] = (int) best[i];
        }
    }