2013-03-03 97 views
0

我在模拟退火算法解决n皇后问题有一些麻烦。基本上,我已经找到了更好的方法,这很好,但是我运行了一个公式来检查它是否应该采取“坏”的行动。根据我的理解,公式是e ^(电路板状态计算的变化)/ CurrentTemperature。这个数字应该与随机双数或浮点数进行比较,如果随机数大于等式,算法应该采取“坏”的举动。那我得到的问题是,该公式始终为真正接近1或超过1这里是一些我的代码(让我知道如果有更多的应提供):模拟退火N皇后概率论坛

temperature = n*100; //initializes starting temperature 
    currentTemp = n*100; 
    int cooldown = n*2; //initializes cool down temperature 
    float examine = 0; //this is the change in board calculation 
int cost = 1; 
    boolean betterMove = false; 
    queen = new int[n]; 
    int[][] board = graph; // generates a board of n size 
    float ran = 0; //random float to compare to 
    double compareAgainst = 0; //formula variable 
cost = calculate(board, n); //calculates the cost 
while (cost > 0 && currentTemp > 0) 
    { 


     // chooses a random queen to move that has a heuristic higher than zero 
     int Q = rand.nextInt(n); 
     while (queen[Q] == 0) 
      Q = rand.nextInt(n); 

     betterMove = false; 

     for (int i = 0; i < n; i++) 
     { 
      for (int j = 0; j < n; j++) 
      { 
       if (board[i][j] == 1 && j == Q) 
       { 
        while (!betterMove) 
        { 
         int move = i; 
         while (move == i) 

         move = rand.nextInt(n); //pick a random move 
         tempBoard[i][j] = 0; //erase old position 
         tempBoard[move][j] = 1; //set new position 

examine = calculate(tempBoard, n) - calculate(board, n); //calculates the difference between the change in boards 
         ran = rand.nextFloat(); //generates random number to compare against 
         compareAgainst = Math.pow(Math.E, (-examine/currentTemp)); //formula out of the book, basically is e^(change in board state divided by currentTemp) 


         if (calculate(tempBoard, n) < calculate(board, n)) //if this is a better move 
         { 
          for (int a = 0; a < n; a++) 
           for (int b = 0; b < n; b++) 
            board[a][b] = tempBoard[a][b]; //set it to the board 

          cost = calculate(board, n); 
          currentTemp -= cooldown; //cool down the temperature 

    betterMove = true; 
         } 

else if(calculate(tempBoard,n) >= calculate(board,n)) //if this is a worse move 
         { 

          if(verbose == 1) //outputs whether or not this is a bad move and outputs function value and random float for simulated annealing purposes 
          { 
           System.out.println("This is a worse move"); 
           System.out.println("The numbers for Simulated Annealing:"); 
           System.out.println("Random number = " + ran); 
           System.out.println("Formula = " + compareAgainst); 
           System.out.println("Examine = " + examine); 

          } 

          if(ran > compareAgainst) //if the random float is greater than compare against, take the bad move 

          { 

           for (int a = 0; a < n; a++) 
            for (int b = 0; b < n; b++) 
             board[a][b] = tempBoard[a][b]; //take the move 

           cost = calculate(board, n); 

           currentTemp-= cooldown; 



           betterMove = true; 
          } 

          else //if not, do not take the move 
          { 

           for (int a = 0; a < n; a++) 
            for (int b = 0; b < n; b++) 
             tempBoard[a][b] = board[a][b]; 



           } 

          currentTemp-= cooldown; 
          betterMove = true; 
          } 
         } 


        } 

        i = n; 
        j = n; 
       } 
      } 
     } 

    } 

我已经尝试了一些诸如使检查变量为负数或取得棋盘状态差异的绝对值等事情。另外,被调用的计算函数基本上扫描板并返回有多少个皇后冲突,这是一个整数。让我知道是否需要更多的澄清。感谢

+0

[这里](https://github.com/droolsjbpm/drools-planner/blob/master /drools-planner-core/src/main/java/org/drools/planner/core/localsearch/decider/acceptor/simulatedannealing/SimulatedAnnealingAcceptor.java#L28)是我在Java中的模拟退火实现,它在N个皇后和[更多高级用例](http://docs.jboss.org/drools/release/5.5.0.Final/drools-planner-docs/html_single/index.html#downloadAndRunTheExamples)。也许它有帮助。它适用于多个分数级别(其中分数超过1就是双倍)。 – 2013-03-04 09:09:01

+0

@GeoffreyDeSmet你好杰弗里,请你再次发送你的密码。我无法打开您的链接。 – svlzx 2013-11-05 23:28:28

+1

@svlzx [这是我现在的SA实现](https://github.com/droolsjbpm/optaplanner/blob/master/optaplanner-core/src/main/java/org/optaplanner/core/impl/localsearch/decider/acceptor /simulatedannealing/SimulatedAnnealingAcceptor.java) – 2013-11-06 07:17:00

回答

0

也许从OptaPlanner“式和实施例此图像以s文件帮助太:

enter image description here