home *** CD-ROM | disk | FTP | other *** search
/ Dream 57 / Amiga_Dream_57.iso / Amiga / Jeux / Reflexion / Crafty-15.19.lha / crafty-15.19 / src / root.c < prev    next >
C/C++ Source or Header  |  1998-09-13  |  8KB  |  174 lines

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include "chess.h"
  4. #include "data.h"
  5. #include "epdglue.h"
  6.  
  7. /* last modified 03/11/97 */
  8. /*
  9. ********************************************************************************
  10. *                                                                              *
  11. *   RootMoveList() is used to set up the ply one move list.  it is a  more     *
  12. *   accurate ordering of the move list than that done for plies deeper than    *
  13. *   one.  briefly, Evaluate() is used to evaluate the positional/material      *
  14. *   score for each move and then the status of friendly pieces is added in.    *
  15. *   EnPrise() evaluates the safety of each friendly piece by noticing          *
  16. *   attackers and defenders and returning the expected loss. Root_Moves()      *
  17. *   is only called once before the iterated search is started.  as the         *
  18. *   iterations progress, the moves in the root move list are continually       *
  19. *   re-arranged as scores are backed up to the root of the tree.               *
  20. *                                                                              *
  21. ********************************************************************************
  22. */
  23. void RootMoveList(int wtm)
  24. {
  25.   int *mvp, tempm;
  26.   int square, i, side, done, temp, value;
  27.   TREE *tree=local[0];
  28.   int tb_value;
  29. /*
  30.  ----------------------------------------------------------
  31. |                                                          |
  32. |   if the position at the root is a draw, based on EGTB   |
  33. |   results, we are going to behave differently.  we will  |
  34. |   extract the root moves that are draws, and toss the    |
  35. |   losers out.  then, we will do a normal search on the   |
  36. |   moves that draw to try and chose the most difficult    |
  37. |   drawing move.                                          |
  38. |                                                          |
  39.  ----------------------------------------------------------
  40. */
  41.   EGTB_draw=0;
  42.   if (TotalPieces<=5 && EGTBScore(tree, 1, wtm, &tb_value)) {
  43.     if (tb_value == 0) {
  44.       if ((wtm && Material>0) || (!wtm && Material<0)) EGTB_draw=1;
  45.     }
  46.   }
  47. /*
  48.  ----------------------------------------------------------
  49. |                                                          |
  50. |   first, use GenerateMoves() to generate the set of      |
  51. |   legal moves from the root position.                    |
  52. |                                                          |
  53.  ----------------------------------------------------------
  54. */
  55.   easy_move=0;
  56.   tree->last[1]=GenerateCaptures(tree, 1, wtm, tree->last[0]);
  57.   tree->last[1]=GenerateNonCaptures(tree, 1, wtm, tree->last[1]);
  58.   if (tree->last[1] == tree->last[0]+1) return;
  59. /*
  60.  ----------------------------------------------------------
  61. |                                                          |
  62. |   now make each move and use Evaluate() to compute the   |
  63. |   positional evaluation.                                 |
  64. |                                                          |
  65.  ----------------------------------------------------------
  66. */
  67.   for (mvp=tree->last[0];mvp<tree->last[1];mvp++) {
  68.     value=-4000000;
  69.     MakeMove(tree, 1, *mvp, wtm);
  70.     if (!Check(wtm)) do {
  71.       if (EGTB_draw) {
  72.         i=EGTBScore(tree, 2, ChangeSide(wtm), &tb_value);
  73.         if (tb_value != 0) break;
  74.       }
  75.       tree->current_move[1]=*mvp;
  76.       value=-Evaluate(tree,2,ChangeSide(wtm),-99999,99999);
  77. /*
  78.  ----------------------------------------------------------
  79. |                                                          |
  80. |   now use EnPrise() to analyze the state of all the      |
  81. |   friendly pieces to see what appears to be hanging when |
  82. |   we try the current move.                               |
  83. |                                                          |
  84.  ----------------------------------------------------------
  85. */
  86.       side=(wtm) ? 1 : -1;
  87.       for (square=0;square<64;square++) 
  88.         if (PieceOnSquare(square)*side > 0)
  89.           value-=Max(EnPrise(square,ChangeSide(wtm)),0);
  90. /*
  91.  ----------------------------------------------------------
  92. |                                                          |
  93. |   add in a bonus if this move is part of the previous    |
  94. |   principal variation.  it was good in the search, we    |
  95. |   should try it first now.                               |
  96. |                                                          |
  97.  ----------------------------------------------------------
  98. */
  99.  
  100.       if((Piece(*mvp)    == Piece(last_pv.path[1])) &&
  101.          (From(*mvp)     == From(last_pv.path[1])) &&
  102.          (To(*mvp)       == To(last_pv.path[1])) &&
  103.          (Captured(*mvp) == Captured(last_pv.path[1])) &&
  104.          (Promote(*mvp)  == Promote(last_pv.path[1]))) {
  105.         value+=2000000;
  106.     }
  107. /*
  108.  ----------------------------------------------------------
  109. |                                                          |
  110. |   fudge the score for promotions so that promotion to a  |
  111. |   queen is tried first.  since the positional score is   |
  112. |   computed before the piece is removed, under-promoting  |
  113. |   sometimes looks better.                                |
  114. |                                                          |
  115.  ----------------------------------------------------------
  116. */
  117.       if (Promote(*mvp) && (Promote(*mvp) != queen)) value-=50;
  118.     } while(0);
  119.     tree->sort_value[mvp-tree->last[0]]=value;
  120.     UnMakeMove(tree, 1, *mvp, wtm);
  121.   }
  122. /*
  123.  ----------------------------------------------------------
  124. |                                                          |
  125. |   now sort the moves into order based on the sum of the  |
  126. |   positional score less the possible hung pieces, and    |
  127. |   factoring in a bonus for following the PV move.        |
  128. |                                                          |
  129.  ----------------------------------------------------------
  130. */
  131.   do {
  132.     done=1;
  133.     for (i=0;i<tree->last[1]-tree->last[0]-1;i++) {
  134.       if (tree->sort_value[i] < tree->sort_value[i+1]) {
  135.         temp=tree->sort_value[i];
  136.         tree->sort_value[i]=tree->sort_value[i+1];
  137.         tree->sort_value[i+1]=temp;
  138.         tempm=*(tree->last[0]+i);
  139.         *(tree->last[0]+i)=*(tree->last[0]+i+1);
  140.         *(tree->last[0]+i+1)=tempm;
  141.         done=0;
  142.       }
  143.     }
  144.   } while(!done);
  145. /*
  146.  ----------------------------------------------------------
  147. |                                                          |
  148. |   now trim the move list to eliminate those moves that   |
  149. |   "hung" the king and are illegal.                       |
  150. |                                                          |
  151.  ----------------------------------------------------------
  152. */
  153.   for (;tree->last[1]>tree->last[0];tree->last[1]--) 
  154.     if (tree->sort_value[tree->last[1]-tree->last[0]-1] > -3000000) break;
  155.   if (tree->sort_value[0] > 1000000) tree->sort_value[0]-=2000000;
  156.   if (tree->sort_value[0] > tree->sort_value[1]+200 &&
  157.       ((To(*tree->last[0]) == To(last_opponent_move) &&
  158.         Captured(*tree->last[0]) == Piece(last_opponent_move)) || 
  159.       tree->sort_value[0] < PAWN_VALUE)) easy_move=1;
  160.   if (trace_level > 0) {
  161.     printf("produced %d moves at root\n",tree->last[1]-tree->last[0]);
  162.     for (mvp=tree->last[0];mvp<tree->last[1];mvp++) {
  163.       tree->current_move[1]=*mvp;
  164.       printf("%s",OutputMove(tree,*mvp,1,wtm));
  165.       MakeMove(tree, 1, *mvp, wtm);
  166.       printf("/%d/%d  ",tree->sort_value[mvp-tree->last[0]],
  167.              -Evaluate(tree,2,ChangeSide(wtm),-99999,99999));
  168.       if (!((mvp-tree->last[0]+1) % 5)) printf("\n");
  169.       UnMakeMove(tree, 1, *mvp, wtm);
  170.     }
  171.   }
  172.   return;
  173. }
  174.