zoukankan      html  css  js  c++  java
  • x01.Weiqi.8: 一点改进

    原来的代码全部删除,进行了深层次重构,得其意而忘其言。得意之处有二:

    1.关于显示

    以 StoneSize 属性为依托,在 set 中加了一句:Width = Height = m_StoneSize * 19;以此来控制棋盘大小。所有的对象在 Init() 方法中创建,而具体的渲染在 Redraw() 方法中完成。这种创建与重绘相分开的办法,使调整大小时进行重绘更简单易行。这两个方法的代码如下:

     1 void Init()
     2         {
     3             // 线
     4             for (int i = 0; i < 19; i++) {
     5                 m_LinesH[i] = new Line();
     6                 m_LinesH[i].Stroke = Brushes.Black;
     7                 m_Canvas.Children.Add(m_LinesH[i]);
     8 
     9                 m_LinesV[i] = new Line();
    10                 m_LinesV[i].Stroke = Brushes.Black;
    11                 m_Canvas.Children.Add(m_LinesV[i]);
    12             }
    13 
    14             //
    15             for (int j = 0; j < 3; j++) {
    16                 for (int i = 0; i < 3; i++) {
    17                     m_Stars[i, j] = new Ellipse();
    18                     m_Stars[i, j].Fill = Brushes.Black;
    19                     m_Canvas.Children.Add(m_Stars[i, j]);
    20                 }
    21             }
    22 
    23             for (int i = 0; i < 19; i++) {
    24                 for (int j = 0; j < 19; j++) {
    25                     m_Stones[i, j] = new Ellipse();
    26                     m_Stones[i, j].Visibility = Visibility.Hidden;
    27                     m_Canvas.Children.Add(m_Stones[i, j]);
    28 
    29                     m_Numbers[i, j] = new TextBlock();
    30                     m_Numbers[i, j].Background = Brushes.Transparent;
    31                     m_Numbers[i, j].Visibility = Visibility.Hidden;
    32                     m_Canvas.Children.Add(m_Numbers[i, j]);
    33 
    34                     m_Steps[i, j] = new Step();
    35                     m_Steps[i, j].Row = i;
    36                     m_Steps[i, j].Col = j;
    37                     m_EmptySteps.Add(m_Steps[i, j]);
    38                     m_AllSteps.Add(m_Steps[i, j]);
    39                 }
    40             }
    41 
    42             // 当前标志
    43             m_CurrentRect.Visibility = System.Windows.Visibility.Hidden;
    44             m_CurrentRect.Fill = Brushes.Red;
    45             m_Canvas.Children.Add(m_CurrentRect);
    46 
    47             for (int i = 0; i < 19; i++) {
    48                 for (int j = 0; j < 19; j++) {
    49                     Rectangle rect = new Rectangle();
    50                     rect.Visibility = System.Windows.Visibility.Hidden;
    51                     m_EmptyRects[i, j] = rect;
    52                     m_Canvas.Children.Add(m_EmptyRects[i,j]);
    53 
    54                 }
    55             }
    56         }
    Init()
      1 public void Redraw()
      2         {
      3             // 画线
      4             for (int i = 0; i < 19; i++) {
      5                 Line l = m_LinesH[i];
      6                 int y = i * StoneSize + StoneSize / 2;
      7                 l.X1 = StoneSize / 2;
      8                 l.Y1 = y;
      9                 l.X2 = 19 * StoneSize - StoneSize / 2;
     10                 l.Y2 = y;
     11 
     12                 l = m_LinesV[i];
     13                 int x = i * StoneSize + StoneSize / 2;
     14                 l.X1 = x;
     15                 l.Y1 = StoneSize / 2;
     16                 l.X2 = x;
     17                 l.Y2 = 19 * StoneSize - StoneSize / 2;
     18             }
     19 
     20             // 画星
     21             for (int j = 0; j < 3; j++) {
     22                 for (int i = 0; i < 3; i++) {
     23                     Ellipse e = m_Stars[i, j];
     24                     e.Width = e.Height = StoneSize / 3;
     25                     double left = 4 * StoneSize + j * 6 * StoneSize - StoneSize / 2 - e.Width / 2;
     26                     double top = 4 * StoneSize + i * 6 * StoneSize - StoneSize / 2 - e.Height / 2;
     27                     Canvas.SetLeft(e, left);
     28                     Canvas.SetTop(e, top);
     29                 }
     30             }
     31 
     32             // Stones and Numbers
     33             for (int i = 0; i < 19; i++) {
     34                 for (int j = 0; j < 19; j++) {
     35                     var stone = m_Stones[i, j];
     36                     stone.Width = stone.Height = StoneSize;
     37                     Canvas.SetLeft(stone, j * StoneSize);
     38                     Canvas.SetTop(stone, i * StoneSize);
     39 
     40                     ShowNumber(i, j, m_Steps[i, j].StepCount);
     41                 }
     42             }
     43 
     44             // 点目标志
     45             if (IsShowMesh)
     46                 for (int i = 0; i < 19; i++) {
     47                     for (int j = 0; j < 19; j++) {
     48                         var rect = m_EmptyRects[i, j];
     49                         rect.Width = rect.Height = m_CurrentRect.Width;
     50                         double offset = (StoneSize - rect.Width) / 2.0;
     51                         Canvas.SetLeft(rect, j * StoneSize + offset);
     52                         Canvas.SetTop(rect, i * StoneSize + offset);
     53                     }
     54                 }
     55         }
     56 
     57         public bool NextOne(int row, int col)
     58         {
     59             if (m_Steps[row, col].StoneColor != StoneColor.Empty)
     60                 return false;
     61             if (m_BanOnce.Row == row && m_BanOnce.Col == col) {
     62                 return false;
     63             }
     64             m_BanOnce.Row = m_BanOnce.Col = -1;
     65 
     66             DrawStep(row, col);
     67             bool isBlack;
     68             if (m_Steps[row, col].StoneColor == StoneColor.Black) {
     69                 m_BlackSteps.Add(m_Steps[row, col]);
     70                 isBlack = true;
     71             } else {
     72                 m_WhiteSteps.Add(m_Steps[row, col]);
     73                 isBlack = false;
     74             }
     75             m_EmptySteps.Remove(m_Steps[row, col]);
     76 
     77             UpdateBlackBlocks();
     78             UpdateWhiteBlocks();
     79             if (isBlack) {
     80                 if (!UpdateDeadBlocks(m_WhiteBlocks))
     81                     UpdateDeadBlocks(m_BlackBlocks);
     82             } else {
     83                 if (!UpdateDeadBlocks(m_BlackBlocks))
     84                     UpdateDeadBlocks(m_WhiteBlocks);
     85             }
     86 
     87             MoveCurrentRect();
     88 
     89             m_StepCount++;
     90 
     91             StoneColor selfColor = isBlack ? StoneColor.Black : StoneColor.White;
     92             bool isKillSelf = m_DeadBlocks.ContainsKey(m_StepCount - 1)
     93                     && m_DeadBlocks[m_StepCount - 1].Steps.Count == 1
     94                     && m_DeadBlocks[m_StepCount - 1].Steps[0].StoneColor == selfColor;
     95             if (isKillSelf) {
     96                 m_DeadBlocks.Remove(m_StepCount - 1);
     97                 BackOne();
     98                 return false;
     99             }
    100 
    101             return true;
    102         }
    Redraw()

    2.关于提子

    以 LinkSteps()方法为依托,提子不再是上下左右一通乱吃了,而是采用集合的办法,只需看看一块棋有没有气即可。其代码如下:

     1 //   +
     2         // + + +    与 step 相连的棋子,包含自身
     3         //   +        根据 color 参数决定是所有,同色,黑色,白色,还是空色。
     4         List<Step> LinkSteps(Step step, StoneColor color = StoneColor.Empty)
     5         {
     6             List<Step> links = new List<Step>();
     7             for (int i = -1; i < 2; i++) {
     8                 for (int j = -1; j < 2; j++) {
     9                     if (i == j || i == -j) {
    10                         continue;
    11                     }
    12                     if (InRange(step.Row + i, step.Col + j)) {
    13                         links.Add(m_Steps[step.Row + i, step.Col + j]);
    14                     }
    15                 }
    16             }
    17             links.Add(step);
    18             if (color == StoneColor.All) {
    19                 return links;
    20             } else {
    21                 links.RemoveAll(l => l.StoneColor != color);
    22                 return links;
    23             }
    24         }
    LinkSteps()

    当然,关于劫争,关于悔棋,非深入代码,不能明白。但 LinkSteps()是构成集合的基础。从集合的观点,研究围棋,相信比其他方法更为可行。

  • 相关阅读:
    深入了解Struts2返回JSON数据的原理及具体应用范例
    Struts国际化
    LeetCode Balanced Binary Tree
    LeetCode Triangle
    Binary Tree Level Order Traversal
    Pow(x,n)
    Symmetric Tree
    LeetCode Word Search
    LeetCode Insert Interval
    Maximum Depth of Binary Tree
  • 原文地址:https://www.cnblogs.com/china_x01/p/4522618.html
Copyright © 2011-2022 走看看