예제 #1
0
    /// <summary>
    /// Moves an randomly chosen element in the specified <paramref name="permutation"/> array 
    /// to another randomly generated position.
    /// </summary>
    /// <param name="random">The random number generator.</param>
    /// <param name="permutation">The permutation to manipulate.</param>
    public static void Apply(IRandom random, Permutation permutation) {
      Permutation original = (Permutation)permutation.Clone();
      int cutIndex, insertIndex, number;

      cutIndex = random.Next(original.Length);
      insertIndex = random.Next(original.Length);
      number = original[cutIndex];

      int i = 0;  // index in new permutation
      int j = 0;  // index in old permutation
      while (i < original.Length) {
        if (j == cutIndex) {
          j++;
        }
        if (i == insertIndex) {
          permutation[i] = number;
          i++;
        }
        if ((i < original.Length) && (j < original.Length)) {
          permutation[i] = original[j];
          i++;
          j++;
        }
      }
    }
        /// <summary>
        /// Moves an randomly chosen element in the specified <paramref name="permutation"/> array
        /// to another randomly generated position.
        /// </summary>
        /// <param name="random">The random number generator.</param>
        /// <param name="permutation">The permutation to manipulate.</param>
        public static void Apply(IRandom random, Permutation permutation)
        {
            Permutation original = (Permutation)permutation.Clone();
            int         cutIndex, insertIndex, number;

            cutIndex    = random.Next(original.Length);
            insertIndex = random.Next(original.Length);
            number      = original[cutIndex];

            int i = 0; // index in new permutation
            int j = 0; // index in old permutation

            while (i < original.Length)
            {
                if (j == cutIndex)
                {
                    j++;
                }
                if (i == insertIndex)
                {
                    permutation[i] = number;
                    i++;
                }
                if ((i < original.Length) && (j < original.Length))
                {
                    permutation[i] = original[j];
                    i++;
                    j++;
                }
            }
        }
예제 #3
0
 private static void ExchangeSubsequences(Permutation p1, int index1, Permutation p2, int index2, int subSequenceLength) {
   var aux = (Permutation)p1.Clone();
   for (int i = 0; i < subSequenceLength; i++) {
     p1[i + index1] = p2[i + index2];
     p2[i + index2] = aux[i + index1];
   }
 }
        public static void Apply(Permutation permutation, int breakPoint1, int breakPoint2, int insertPoint)
        {
            Permutation original = (Permutation)permutation.Clone();

            int i = 0; // index in new permutation
            int j = 0; // index in old permutation

            while (i < original.Length)
            {
                if (i == insertPoint) // copy translocated area
                {
                    for (int k = breakPoint1; k <= breakPoint2; k++)
                    {
                        permutation[i] = original[k];
                        i++;
                    }
                }
                if (j == breakPoint1) // skip area between breakpoints
                {
                    j = breakPoint2 + 1;
                }
                if ((i < original.Length) && (j < original.Length))
                {
                    permutation[i] = original[j];
                    i++;
                    j++;
                }
            }
        }
    /// <summary>
    /// Moves a randomly chosen interval of elements to another (randomly chosen) position in the given
    /// <paramref name="permutation"/> array and reverses it.
    /// </summary>
    /// <param name="random">The random number generator.</param>
    /// <param name="permutation">The permutation array to manipulate.</param>
    public static void Apply(IRandom random, Permutation permutation) {
      Permutation original = (Permutation)permutation.Clone();
      int breakPoint1, breakPoint2, insertPoint, insertPointLimit;

      breakPoint1 = random.Next(original.Length - 1);
      breakPoint2 = random.Next(breakPoint1 + 1, original.Length);
      insertPointLimit = original.Length - breakPoint2 + breakPoint1 - 1;  // get insertion point in remaining part
      if (insertPointLimit > 0)
        insertPoint = random.Next(insertPointLimit);
      else
        insertPoint = 0;

      int i = 0;  // index in new permutation
      int j = 0;  // index in old permutation
      while (i < original.Length) {
        if (i == insertPoint) {  // copy translocated area
          for (int k = breakPoint2; k >= breakPoint1; k--) {
            permutation[i] = original[k];
            i++;
          }
        }
        if (j == breakPoint1) {  // skip area between breakpoints
          j = breakPoint2 + 1;
        }
        if ((i < original.Length) && (j < original.Length)) {
          permutation[i] = original[j];
          i++;
          j++;
        }
      }
    }
예제 #6
0
        public static void Apply(Permutation permutation, int startIndex, int[] scrambleArray)
        {
            Permutation original = (Permutation)permutation.Clone();

            for (int i = 0; i < scrambleArray.Length; i++) // scramble permutation between breakpoints
            {
                permutation[startIndex + i] = original[startIndex + scrambleArray[i]];
            }
        }
예제 #7
0
        /// <summary>
        /// Moves a randomly chosen interval of elements to another (randomly chosen) position in the given
        /// <paramref name="permutation"/> array and reverses it.
        /// </summary>
        /// <param name="random">The random number generator.</param>
        /// <param name="permutation">The permutation array to manipulate.</param>
        public static void Apply(IRandom random, Permutation permutation)
        {
            Permutation original = (Permutation)permutation.Clone();
            int         breakPoint1, breakPoint2, insertPoint, insertPointLimit;

            breakPoint1      = random.Next(original.Length - 1);
            breakPoint2      = random.Next(breakPoint1 + 1, original.Length);
            insertPointLimit = original.Length - breakPoint2 + breakPoint1 - 1; // get insertion point in remaining part
            if (insertPointLimit > 0)
            {
                insertPoint = random.Next(insertPointLimit);
            }
            else
            {
                insertPoint = 0;
            }

            int i = 0; // index in new permutation
            int j = 0; // index in old permutation

            while (i < original.Length)
            {
                if (i == insertPoint) // copy translocated area
                {
                    for (int k = breakPoint2; k >= breakPoint1; k--)
                    {
                        permutation[i] = original[k];
                        i++;
                    }
                }
                if (j == breakPoint1) // skip area between breakpoints
                {
                    j = breakPoint2 + 1;
                }
                if ((i < original.Length) && (j < original.Length))
                {
                    permutation[i] = original[j];
                    i++;
                    j++;
                }
            }
        }
    public static void Apply(Permutation permutation, int breakPoint1, int breakPoint2, int insertPoint) {
      Permutation original = (Permutation)permutation.Clone();

      int i = 0;  // index in new permutation
      int j = 0;  // index in old permutation
      while (i < original.Length) {
        if (i == insertPoint) {  // copy translocated area
          for (int k = breakPoint1; k <= breakPoint2; k++) {
            permutation[i] = original[k];
            i++;
          }
        }
        if (j == breakPoint1) {  // skip area between breakpoints
          j = breakPoint2 + 1;
        }
        if ((i < original.Length) && (j < original.Length)) {
          permutation[i] = original[j];
          i++;
          j++;
        }
      }
    }
 public static void Apply(Permutation permutation, int startIndex, int[] scrambleArray) {
   Permutation original = (Permutation)permutation.Clone();
   for (int i = 0; i < scrambleArray.Length; i++) {  // scramble permutation between breakpoints
     permutation[startIndex + i] = original[startIndex + scrambleArray[i]];
   }
 }
 public static double EvaluateMove(Permutation tour, InversionMove move, Func<int, int, double> distance, DoubleArray probabilities) {
   var afterMove = (Permutation)tour.Clone();
   InversionManipulator.Apply(afterMove, move.Index1, move.Index2);
   return AnalyticalProbabilisticTravelingSalesmanProblem.Evaluate(afterMove, distance, probabilities);
 }
    public static double EvaluateMove(Permutation tour, TranslocationMove move, Func<int, int, double> distance, ItemList<BoolArray> realizations) {
      var afterMove = (Permutation)tour.Clone();
      TranslocationManipulator.Apply(afterMove, move.Index1, move.Index1, move.Index3);
      double moveQuality = 0;
      var edges = new int[12];
      var indices = new int[12];
      edges[0] = tour.GetCircular(move.Index1 - 1);
      indices[0] = DecreaseCircularIndex(tour.Length, move.Index1);
      edges[1] = tour[move.Index1];
      indices[1] = move.Index1;
      edges[2] = tour[move.Index1];
      indices[2] = move.Index1;
      edges[3] = tour.GetCircular(move.Index1 + 1);
      indices[3] = IncreaseCircularIndex(tour.Length, move.Index1);

      edges[6] = afterMove.GetCircular(move.Index3 - 1);
      indices[6] = DecreaseCircularIndex(afterMove.Length, move.Index3);
      edges[7] = afterMove[move.Index3];
      indices[7] = move.Index3;
      edges[8] = afterMove[move.Index3];
      indices[8] = move.Index3;
      edges[9] = afterMove.GetCircular(move.Index3 + 1);
      indices[9] = IncreaseCircularIndex(afterMove.Length, move.Index3);

      if (move.Index3 > move.Index1) {
        edges[4] = tour[move.Index3];
        indices[4] = move.Index3;
        edges[5] = tour.GetCircular(move.Index3 + 1);
        indices[5] = indices[9];
        edges[10] = afterMove.GetCircular(move.Index1 - 1);
        indices[10] = indices[0];
        edges[11] = afterMove[move.Index1];
        indices[11] = move.Index1;
      } else {
        edges[4] = tour.GetCircular(move.Index3 - 1);
        indices[4] = indices[6];
        edges[5] = tour[move.Index3];
        indices[5] = move.Index3;
        edges[10] = afterMove[move.Index1];
        indices[10] = move.Index1;
        edges[11] = afterMove.GetCircular(move.Index1 + 1);
        indices[11] = indices[3];
      }
      int[] aPosteriori = new int[12];
      foreach (var realization in realizations) {
        for (int i = 0; i < edges.Length; i++) {
          Permutation tempPermutation;
          if (i < 6) {
            tempPermutation = tour;
          } else {
            tempPermutation = afterMove;
          }
          if (realization[edges[i]]) {
            aPosteriori[i] = edges[i];
          } else {
            int j = 1;
            if (i % 2 == 0) {
              // find nearest predecessor in realization if source edge
              while (!realization[tempPermutation.GetCircular(indices[i] - j)]) {
                j++;
              }
              aPosteriori[i] = tempPermutation.GetCircular(indices[i] - j);
            } else {
              // find nearest successor in realization if target edge
              while (!realization[tempPermutation.GetCircular(indices[i] + j)]) {
                j++;
              }
              aPosteriori[i] = tempPermutation.GetCircular(indices[i] + j);
            }
          }
        }
        if (!(aPosteriori[0] == aPosteriori[2] && aPosteriori[1] == aPosteriori[3]) &&
          !(aPosteriori[0] == aPosteriori[4] && aPosteriori[1] == aPosteriori[5]) &&
          !(aPosteriori[2] == aPosteriori[4] && aPosteriori[3] == aPosteriori[5])) {
          // compute cost difference between the two a posteriori solutions
          moveQuality = moveQuality + distance(aPosteriori[6], aPosteriori[7]) + distance(aPosteriori[8], aPosteriori[9]) + distance(aPosteriori[10], aPosteriori[11]);
          moveQuality = moveQuality - distance(aPosteriori[0], aPosteriori[1]) - distance(aPosteriori[2], aPosteriori[3]) - distance(aPosteriori[4], aPosteriori[5]);
        }
        Array.Clear(aPosteriori, 0, aPosteriori.Length);
      }
      // return average of cost differences
      return moveQuality / realizations.Count;
    }