/** The main loop for the background thread. It is here that most of the work os orchestrated. */
  public void run() {

    double thisCost = 500.0;
    double oldCost = 0.0;
    double dcost = 500.0;
    int countSame = 0;

    map.update(map.getGraphics());

    while (countSame < 100) {

      generation++;

      int ioffset = matingPopulationSize;
      int mutated = 0;

      // Mate the chromosomes in the favoured population
      // with all in the mating population
      for (int i = 0; i < favoredPopulationSize; i++) {
        Chromosome cmother = chromosomes[i];
        // Select partner from the mating population
        int father = (int) (0.999999 * Math.random() * (double) matingPopulationSize);
        Chromosome cfather = chromosomes[father];

        mutated += cmother.mate(cfather, chromosomes[ioffset], chromosomes[ioffset + 1]);
        ioffset += 2;
      }

      // The new generation is in the matingPopulation area
      // move them to the correct area for sort.
      for (int i = 0; i < matingPopulationSize; i++) {
        chromosomes[i] = chromosomes[i + matingPopulationSize];
        chromosomes[i].calculateCost(cities);
      }

      // Now sort the new mating population
      Chromosome.sortChromosomes(chromosomes, matingPopulationSize);

      double cost = chromosomes[0].getCost();
      dcost = Math.abs(cost - thisCost);
      thisCost = cost;
      double mutationRate = 100.0 * (double) mutated / (double) matingPopulationSize;

      NumberFormat nf = NumberFormat.getInstance();
      nf.setMinimumFractionDigits(2);
      nf.setMinimumFractionDigits(2);

      status.setText(
          "Generation "
              + generation
              + " Cost "
              + (int) thisCost
              + " Mutated "
              + nf.format(mutationRate)
              + "%");

      if ((int) thisCost == (int) oldCost) {
        countSame++;
      } else {
        countSame = 0;
        oldCost = thisCost;
      }
      map.update(map.getGraphics());
    }
    status.setText("Solution found after " + generation + " generations.");
  }