Advertisement
thienlang

AI caro chess 1

Mar 23rd, 2014
378
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 18.72 KB | None | 0 0
  1. class AI
  2.     {
  3.         int n;
  4.         Random rand;
  5.         //int[] TScore = { 0, 7, 9, 85, 769 };
  6.         int[] TScore = { 0, 1, 9, 85, 769 };
  7.         int[] KScore = { 0, 4, 28, 256, 2308 };
  8.         int[,] Val;
  9.         private int maxdepth;
  10.         char _computer;
  11.         char _player;
  12.         int _branch;
  13.         const int INT_MAX = 2147483647;
  14.         private bool zingLaw;
  15.         public char computer
  16.         {
  17.             get
  18.             {
  19.                 return _computer;
  20.             }
  21.             set
  22.             {
  23.                 if (value == 'x')
  24.                     _player = 'o';
  25.                 else
  26.                     _player = 'x';
  27.                 _computer = value;
  28.             }
  29.         }
  30.         public Position prevp, currp;
  31.         void ResetVal()
  32.         {
  33.             for (int i = 0; i < n; i++)
  34.                 for (int j = 0; j < n; j++)
  35.                     Val[i, j] = 0;
  36.         }
  37.         public AI(int size, int ai,bool zingLaw)
  38.         {
  39.             n = size;
  40.             this.zingLaw = zingLaw;
  41.             rand = new Random();
  42.             Val = new int[n, n];
  43.             _branch = 3;
  44.             maxdepth = ai;
  45.             prevp = new Position(-1, -1);
  46.             currp = new Position(-1, -1);
  47.         }
  48.         public void EvalueCaroBoard(ref CaroBoard b, char Player)
  49.         {
  50.             n = b.size;
  51.             ResetVal();
  52.             int rw, cl, i;
  53.             int cComputer, cPlayer;
  54.             //kiem tra hang
  55.             for (rw = 0; rw < n; rw++)
  56.                 for (cl = 0; cl < n - 4; cl++)
  57.                 {
  58.                     cComputer = 0; cPlayer = 0;
  59.                     for (i = 0; i < 5; i++)
  60.                     {
  61.                         if (b.cells[rw, cl + i] == _computer) cComputer++;
  62.                         if (b.cells[rw, cl + i] == _player) cPlayer++;
  63.                     }
  64.                     if (cComputer * cPlayer == 0 && cComputer != cPlayer)
  65.                         for (i = 0; i < 5; i++)
  66.                             if (b.cells[rw, cl + i] == ' ')
  67.                             {
  68.                                 if (cComputer == 0)
  69.                                 {
  70.                                     if (Player == _computer) Val[rw, cl + i] += TScore[cPlayer];
  71.                                     else Val[rw, cl + i] += KScore[cPlayer];
  72.                                     if (zingLaw && b.CheckPosition(rw, cl - 1) && b.CheckPosition(rw, cl + 5) && b.cells[rw, cl - 1] == _computer && b.cells[rw, cl + 5] == _computer)
  73.                                         Val[rw, cl + i] = 0;
  74.                                 }
  75.                                 if (cPlayer == 0)
  76.                                 {
  77.                                     if (Player == _player) Val[rw, cl + i] += TScore[cComputer];
  78.                                     else Val[rw, cl + i] += KScore[cComputer];
  79.                                     if (zingLaw && b.CheckPosition(rw, cl - 1) && b.CheckPosition(rw, cl + 5) && b.cells[rw, cl - 1] == _player && b.cells[rw, cl + 5] == _player)
  80.                                         Val[rw, cl + i] = 0;
  81.                                 }
  82.                                 if (zingLaw && (cComputer == 4 || cPlayer == 4) && ((b.CheckPosition(rw, cl + i - 1) && b.cells[rw, cl + i - 1] == ' ') || (b.CheckPosition(rw, cl + i + 1) && b.cells[rw, cl + i + 1] == ' ')))
  83.                                     Val[rw, cl + i] *= 2;
  84.                                 else if (cComputer == 4 || cPlayer == 4)
  85.                                     Val[rw, cl + i] *= 2;
  86.                             }
  87.                 }
  88.             //Cot
  89.             for (rw = 0; rw < n - 4; rw++)
  90.                 for (cl = 0; cl < n; cl++)
  91.                 {
  92.                     cComputer = 0; cPlayer = 0;
  93.                     for (i = 0; i < 5; i++)
  94.                     {
  95.                         if (b.cells[rw + i, cl] == _computer) cComputer++;
  96.                         if (b.cells[rw + i, cl] == _player) cPlayer++;
  97.                     }
  98.                     if (cComputer * cPlayer == 0 && cComputer != cPlayer)
  99.                         for (i = 0; i < 5; i++)
  100.                             if (b.cells[rw + i, cl] == ' ')
  101.                             {
  102.                                 if (cComputer == 0)
  103.                                 {
  104.                                     if (Player == _computer) Val[rw + i, cl] += TScore[cPlayer];
  105.                                     else Val[rw + i, cl] += KScore[cPlayer];
  106.                                     if (zingLaw && b.CheckPosition(rw - 1, cl) && b.CheckPosition(rw + 5, cl) && b.cells[rw - 1, cl] == _computer && b.cells[rw + 5, cl] == _computer)
  107.                                         Val[rw + i, cl] = 0;
  108.                                 }
  109.                                 if (cPlayer == 0)
  110.                                 {
  111.                                     if (Player == _player) Val[rw + i, cl] += TScore[cComputer];
  112.                                     else Val[rw + i, cl] += KScore[cComputer];
  113.                                     if (zingLaw && b.CheckPosition(rw - 1, cl) && b.CheckPosition(rw + 5, cl) && b.cells[rw - 1, cl] == _player && b.cells[rw + 5, cl] == _player)
  114.                                         Val[rw + i, cl] = 0;
  115.                                 }
  116.                                 if (zingLaw && (cComputer == 4 || cPlayer == 4) && ((b.CheckPosition(rw + i - 1, cl) && b.cells[rw + i - 1, cl] == ' ') || (b.CheckPosition(rw + i + 1, cl) && b.cells[rw + i + 1, cl] == ' ')))
  117.                                     Val[rw + i, cl] *= 2;
  118.                                 else if (cComputer == 4 || cPlayer == 4)
  119.                                     Val[rw + i, cl] *= 2;
  120.                             }
  121.                 }
  122.             //Duong cheo xuong
  123.             for (rw = 0; rw < n - 4; rw++)
  124.                 for (cl = 0; cl < n - 4; cl++)
  125.                 {
  126.                     cComputer = 0; cPlayer = 0;
  127.                     for (i = 0; i < 5; i++)
  128.                     {
  129.                         if (b.cells[rw + i, cl + i] == _computer) cComputer++;
  130.                         if (b.cells[rw + i, cl + i] == _player) cPlayer++;
  131.                     }
  132.                     //Luong gia..
  133.                     if (cComputer * cPlayer == 0 && cComputer != cPlayer)
  134.                         for (i = 0; i < 5; i++)
  135.                             if (b.cells[rw + i, cl + i] == ' ')
  136.                             {
  137.                                 if (cComputer == 0)
  138.                                 {
  139.                                     if (Player == _computer) Val[rw + i, cl + i] += TScore[cPlayer];
  140.                                     else Val[rw + i, cl + i] += KScore[cPlayer];
  141.                                     if (zingLaw && b.CheckPosition(rw - 1, cl - 1) && b.CheckPosition(rw + 5, cl + 5) && b.cells[rw - 1, cl - 1] == _computer && b.cells[rw + 5, cl + 5] == _computer)
  142.                                         Val[rw + i, cl + i] = 0;
  143.                                 }
  144.                                 if (cPlayer == 0)
  145.                                 {
  146.                                     if (Player == _player) Val[rw + i, cl + i] += TScore[cComputer];
  147.                                     else Val[rw + i, cl + i] += KScore[cComputer];
  148.                                     if (zingLaw && b.CheckPosition(rw - 1, cl - 1) && b.CheckPosition(rw + 5, cl + 5) && b.cells[rw - 1, cl - 1] == _player && b.cells[rw + 5, cl + 5] == _player)
  149.                                         Val[rw + i, cl + i] = 0;
  150.                                 }
  151.                                 if (zingLaw && (cComputer == 4 || cPlayer == 4) && ((b.CheckPosition(rw + i - 1, cl + i - 1) && b.cells[rw + i - 1, cl + i - 1] == ' ') || (b.CheckPosition(rw + i + 1, cl + i + 1) && b.cells[rw + i + 1, cl + i + 1] == ' ')))
  152.                                     Val[rw + i, cl + i] *= 2;
  153.                                 else if (cComputer == 4 || cPlayer == 4)
  154.                                     Val[rw + i, cl + i] *= 2;
  155.                             }
  156.                 }
  157.             //Duong cheo len
  158.             for (rw = 4; rw < n; rw++)
  159.                 for (cl = 0; cl < n - 4; cl++)
  160.                 {
  161.                     cComputer = 0; cPlayer = 0;
  162.                     for (i = 0; i < 5; i++)
  163.                     {
  164.                         if (b.cells[rw - i, cl + i] == _computer) cComputer++;
  165.                         if (b.cells[rw - i, cl + i] == _player) cPlayer++;
  166.                     }
  167.                     //Luong gia..
  168.                     if (cComputer * cPlayer == 0 && cComputer != cPlayer)
  169.                         for (i = 0; i < 5; i++)
  170.                             if (b.cells[rw - i, cl + i] == ' ')
  171.                             {
  172.                                 if (cComputer == 0)
  173.                                 {
  174.                                     if (Player == _computer) Val[rw - i, cl + i] += TScore[cPlayer];
  175.                                     else Val[rw - i, cl + i] += KScore[cPlayer];
  176.                                     if (zingLaw && b.CheckPosition(rw + 1, cl - 1) && b.CheckPosition(rw - 5, cl + 5) && b.cells[rw + 1, cl - 1] == _computer && b.cells[rw - 5, cl + 5] == _computer)
  177.                                         Val[rw - i, cl + i] = 0;
  178.                                 }
  179.                                 if (cPlayer == 0)
  180.                                 {
  181.                                     if (Player == _player) Val[rw - i, cl + i] += TScore[cComputer];
  182.                                     else Val[rw - i, cl + i] += KScore[cComputer];
  183.                                     if (zingLaw && b.CheckPosition(rw + 1, cl - 1) && b.CheckPosition(rw - 5, cl + 5) && b.cells[rw + 1, cl - 1] == _player && b.cells[rw - 5, cl + 5] == _player)
  184.                                         Val[rw + i, cl + i] = 0;
  185.                                 }
  186.                                 if (zingLaw && (cComputer == 4 || cPlayer == 4) && ((b.CheckPosition(rw - i + 1, cl + i - 1) && b.cells[rw - i + 1, cl + i - 1] == ' ') || (b.CheckPosition(rw - i - 1, cl + i + 1) && b.cells[rw - i - 1, cl + i + 1] == ' ')))
  187.                                     Val[rw - i, cl + i] *= 2;
  188.                                 else if (cComputer == 4 || cPlayer == 4)
  189.                                     Val[rw - i, cl + i] *= 2;
  190.                             }
  191.                 }
  192.             //EchoVal();
  193.  
  194.         }
  195.  
  196.  
  197.         void EchoVal()
  198.         {
  199.             Console.Clear();
  200.             for (int i = 0; i < n; i++)
  201.             {
  202.                 for (int j = 0; j < n; j++)
  203.                 {
  204.  
  205.                     Console.Write("{0}{1}", Val[i, j], Space(Val[i, j]));
  206.                 }
  207.                 Console.WriteLine("\n");
  208.             }
  209.         }
  210.         string Space(int x)
  211.         {
  212.             int k = x.ToString().Length;
  213.             string r = "";
  214.             //if (x < 0) k += 1;
  215.             for (int i = 0; i < 4 - k; i++)
  216.                 r += " ";
  217.             return r;
  218.         }
  219.         private State GetMaxNode()
  220.         {
  221.             Position p = new Position(0, 0);
  222.             List<State> list = new List<State>();
  223.             int t = -INT_MAX;
  224.             for (int i = 0; i < n; i++)
  225.                 for (int j = 0; j < n; j++)
  226.                 {
  227.                     if (t < Val[i, j])
  228.                     {
  229.                         t = Val[i, j];
  230.                         p.Set(i, j);
  231.                         list.Clear();
  232.                         list.Add(new State(p, t));
  233.                     }
  234.                     else if (t == Val[i, j])
  235.                     {
  236.                         p.Set(i, j);
  237.                         list.Add(new State(p, t));
  238.                     }
  239.                 }
  240.             for (int i = 0; i < list.Count; i++)
  241.             {
  242.                 Val[list[i].p.x, list[i].p.y] = 0;
  243.                 //Console.WriteLine("{0}-{1}", list[i].p.x, list[i].p.y);
  244.             }
  245.             //Console.WriteLine("----");
  246.             int x = rand.Next(0, list.Count);
  247.             //Val[list[x].p.x, list[x].p.y] = 0;
  248.             return list[x];
  249.         }
  250.         private string[] Truonghopx = { @"\sxx\s", @"\sxxxo", @"oxxx\s", @"\sxxx\s", @"\sxxxxo", @"oxxxx\s", @"\sxxxx\s", @"xxxxx" };
  251.         private string[] Truonghopo = { @"\soo\s", @"\sooox", @"xooo\s", @"\sooo\s", @"\soooox", @"xoooo\s", @"\soooo\s", @"ooooo" };
  252.         private int[] point = { 6, 4, 4, 12, 30, 30, 3000, 10000 };
  253.         private int Eval(ref CaroBoard b)
  254.         {
  255.             string s = "";
  256.             for (int i = 0; i < n; i++)
  257.             {
  258.                 for (int j = 0; j < n; j++)
  259.                     s += b.cells[i, j];
  260.                 s += ";";
  261.                 for (int j = 0; j < n; j++)
  262.                     s += b.cells[j, i];
  263.                 s += ";";
  264.             }
  265.             for (int i = 0; i < n - 4; i++)
  266.             {
  267.                 for (int j = 0; j < n - i; j++)
  268.                     s += b.cells[j, i + j];
  269.                 s += ";";
  270.             }
  271.             for (int i = n - 5; i > 0; i--)
  272.             {
  273.                 for (int j = 0; j < n - i; j++)
  274.                     s += b.cells[i + j, j];
  275.                 s += ";";
  276.             }
  277.             for (int i = 4; i < n; i++)
  278.             {
  279.                 for (int j = 0; j <= i; j++)
  280.                     s += b.cells[i - j, j];
  281.                 s += ";";
  282.             }
  283.             for (int i = n - 5; i > 0; i--)
  284.             {
  285.                 for (int j = n - 1; j >= i; j--)
  286.                     s += b.cells[j, i + n - j - 1];
  287.                 s += ";\n";
  288.             }
  289.             //Console.WriteLine(s);
  290.             Regex regex1, regex2;
  291.             int diem = 0;
  292.             for (int i = 0; i < Truonghopx.Length; i++)
  293.             {
  294.                 regex1 = new Regex(Truonghopx[i]);
  295.                 regex2 = new Regex(Truonghopo[i]);
  296.                 if (_computer == 'o')
  297.                 {
  298.                     diem += point[i] * regex2.Matches(s).Count;
  299.                     diem -= point[i] * regex1.Matches(s).Count;
  300.                 }
  301.                 else
  302.                 {
  303.                     diem -= point[i] * regex2.Matches(s).Count;
  304.                     diem += point[i] * regex1.Matches(s).Count;
  305.                 }
  306.             }
  307.             return diem;
  308.         }
  309.         public Position Solve(ref CaroBoard bb, char Player)
  310.         {
  311.             currp.Set(-1, -1);
  312.             prevp.Set(-1, -1);
  313.             CaroBoard b = new CaroBoard(bb.size,zingLaw);
  314.             for (int i = 0; i < n; i++)
  315.                 for (int j = 0; j < n; j++)
  316.                     b.cells[i, j] = bb.cells[i, j];
  317.             //Console.WriteLine("Current P={0}", Eval(ref b));
  318.             computer = Player;
  319.             EvalueCaroBoard(ref b, _computer);
  320.             //EchoVal();
  321.             List<State> list = new List<State>();
  322.             for (int i = 0; i < _branch; i++)
  323.             {
  324.                 list.Add(GetMaxNode());
  325.                 if (!zingLaw&&list[i].val > 1538) break;
  326.             }
  327.             int maxp = -INT_MAX;
  328.             List<State> ListChoose = new List<State>();
  329.             for (int i = 0; i < list.Count; i++)
  330.             {
  331.                 currp.Set(list[i].p);
  332.                 b.cells[list[i].p.x, list[i].p.y] = _computer;
  333.                 int t = MinVal(ref b, list[i], -INT_MAX, INT_MAX, 0);
  334.                 //Console.WriteLine("{0}-{1}: {2}", list[i].p.x, list[i].p.y, t);//list[i].val);
  335.                 if (maxp < t)
  336.                 {
  337.                     maxp = t;
  338.                     ListChoose.Clear();
  339.                     ListChoose.Add(list[i]);
  340.                 }
  341.                 else if (maxp == t)
  342.                 {
  343.                     ListChoose.Add(list[i]);
  344.                 }
  345.                 b.cells[list[i].p.x, list[i].p.y] = ' ';
  346.             }
  347.             int x = rand.Next(0, ListChoose.Count);
  348.             //Console.Write("i={0};",x);
  349.             return ListChoose[x].p;
  350.         }
  351.         private int MaxVal(ref CaroBoard b, State s, int alpha, int beta, int depth)
  352.         {
  353.             int val = Eval(ref b);
  354.             if (depth >= maxdepth || Math.Abs(val) > 3000) return val;
  355.             EvalueCaroBoard(ref b, _computer);
  356.             List<State> list = new List<State>();
  357.             for (int i = 0; i < _branch; i++)
  358.             {
  359.                 list.Add(GetMaxNode());
  360.                 if (!zingLaw&&list[i].val > 1538) break;
  361.             }
  362.             for (int i = 0; i < list.Count; i++)
  363.             {
  364.                 b.cells[list[i].p.x, list[i].p.y] = _computer;
  365.                 alpha = Math.Max(alpha, MinVal(ref b, list[i], alpha, beta, depth + 1));
  366.                 b.cells[list[i].p.x, list[i].p.y] = ' ';
  367.                 if (alpha > beta) break;
  368.             }
  369.             return alpha;
  370.         }
  371.         private int MinVal(ref CaroBoard b, State s, int alpha, int beta, int depth)
  372.         {
  373.             int val = Eval(ref b);
  374.             if (depth >= maxdepth || Math.Abs(val) > 3000) return val;
  375.             EvalueCaroBoard(ref b, _player);
  376.             List<State> list = new List<State>();
  377.             for (int i = 0; i < _branch; i++)
  378.             {
  379.                 list.Add(GetMaxNode());
  380.                 if (!zingLaw&&list[i].val > 1538) break;
  381.             }
  382.             for (int i = 0; i < list.Count; i++)
  383.             {
  384.                 b.cells[list[i].p.x, list[i].p.y] = _player;
  385.                 beta = Math.Min(beta, MaxVal(ref b, list[i], alpha, beta, depth + 1));
  386.                 b.cells[list[i].p.x, list[i].p.y] = ' ';
  387.                 if (alpha >= beta) break;
  388.             }
  389.             return beta;
  390.         }
  391.         private int NegaScout(ref CaroBoard bb, State s, int alpha, int beta, int depth)
  392.         {
  393.             int val = Eval(ref bb);
  394.             if (depth >= maxdepth || Math.Abs(val) > 3000) return val;
  395.             int b = beta, a;
  396.             if (depth % 2 == 0) EvalueCaroBoard(ref bb, _player);
  397.             else EvalueCaroBoard(ref bb, _computer);
  398.             List<State> list = new List<State>();
  399.             for (int i = 0; i < _branch; i++)
  400.             {
  401.                 list.Add(GetMaxNode());
  402.                 if (!zingLaw&&list[i].val > 1538) break;
  403.             }
  404.             for (int i = 0; i < list.Count; i++)
  405.             {
  406.                 if (depth % 2 == 0) bb.cells[list[i].p.x, list[i].p.y] = _computer;
  407.                 else bb.cells[list[i].p.x, list[i].p.y] = _player;
  408.                 a = -NegaScout(ref bb, list[i], -b, -alpha, depth + 1);
  409.                 if (a > alpha && a < beta && i != 0)
  410.                     a = -NegaScout(ref bb, list[i], -beta, -alpha, depth + 1);
  411.                 bb.cells[list[i].p.x, list[i].p.y] = ' ';
  412.                 alpha = Math.Max(a, alpha);
  413.                 if (alpha >= beta) break;
  414.                 b = alpha + 1;
  415.             }
  416.             return alpha;
  417.         }
  418.     }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement