package org.javagarden.j2me.fivelink.client;
/**
 * 游戏的人式智能处理类。
 *
 */
public class AI
{    /**
     * 找到最佳下棋点。
     * 基本思路是, 先计算每个点的权值,在权值最高的位置下棋
     * @author Turbo Chen
     * @created 2005-5-11
     */ 
    public static Location findBestChessLocation( Player currentPlayer, FiveLinkModel model)
    {
        //权值数组
        int[][] power = new int[FiveLinkModel.BOARD_SIZE][FiveLinkModel.BOARD_SIZE];
        for ( short i = 0; i < FiveLinkModel.BOARD_SIZE; i++ )
        {
            for ( short j = 0; j < FiveLinkModel.BOARD_SIZE; j++ )
            {
                // 当已有子时将该点的权值设为-1
                if ( model.getChess()[i][j] !=0 )
                {
                    power[i][j] = -1; 
                }
                // 否则计算该点权值
                else
                {
                    power[i][j] = (short) calcPower(i, j, currentPlayer,model);
                }
            }
        }
        //计算完所有点的权值后, 再找出其中权值最大的点
        Location bestLoc = calcMaximumPowerLocation(power);
        power = null;
        return bestLoc;    }    /**
     * 找出权值最大点.
     * @param power
     * @return
     */
    private static Location calcMaximumPowerLocation(int[][] power)
    {
        int max = 0;
        short x = 0, y = 0;
        for ( short i = 0; i < FiveLinkModel.BOARD_SIZE; i++ )
        {
            for ( short j = 0; j < FiveLinkModel.BOARD_SIZE; j++ )
            {
                if ( power[i][j] > max )
                {
                    x = i;
                    y = j;
                    max = power[i][j];
                }
            }
        }
        return new Location(x,y);
    }    /**
     * 检查m,n点的权值.<p>
     * 思路是, 假定在m,n位置下棋后,计算4个方向经过该点,同色相连的棋子数量, 不同的数量有不同的
     * 权值,将四个方向上权值相加即为该点的权值.计算完后恢复该点的状态.
     * @param m
     * @param n
     * @param currentPlayer
     * @param model
     * @return
     */
    private static int calcPower(short m, short n,  Player currentPlayer, FiveLinkModel model)
    {
        int p = 0;
        
        //找AI自己的取胜点,
        int p1 = 1000;
        //找AI自己的三个相连的点
        int p3 = 60;
        //找AI自己的两个相连的点
        int p5 = 20;
        //找AI自己的相连的点
        int p7 = 10;        //找对手的取胜点
        int p2 = 85;
        //找对手的三个相连的点
        int p4 = 45;
        //找对手的两个相连的点
        int p6 = 15;
        //找对方的相连的点
        int p8 = 5;
        
        short[] arrLinks = new short[4];
        //如果当是我方下棋, 判断我方所持棋子的颜色, 在该点预下一子, 然后进行后续计算.
        if ( currentPlayer.getChessType()==Player.BLACK )
        {
            //我方是黑子
            model.setChess(m,n,1);
        }else
        {
            //我方是白子
            model.setChess(m,n,-1);
        }
        
        // 计算4个方向上同色相连棋子的数量.
        arrLinks = calcLinkCount(m,n,model.getChess());        //如果m,n是中心点, 将权值加1
        if ( m == FiveLinkModel.BOARD_SIZE/2 && n == FiveLinkModel.BOARD_SIZE/2 )
        {
            p += 1;
        }
        //计算我方在该点四个方向的权值
        for ( short i = 0; i < 4; i++ )
        {
            if ( Math.abs(arrLinks[i]) == 5 )
            {
                p += p1;
            }
            if ( arrLinks[i] == 4 )
            {
                p += p3;
            }
            if ( arrLinks[i] == 3 )
            {
                p += p5;
            }
            if ( arrLinks[i] == 2 )
            {
                p += p7;
            }
        }
        //如果当是对手方下棋, 判断对方所持棋子的颜色, 在该点预下一子, 然后进行后续计算.
        if ( currentPlayer.getChessType()==1 )
        {
            //如果对方是白子, 
            model.setChess(m,n,-1);
        }else
        {
            //如果对方是黑子,
            model.setChess(m,n,1);
        }        arrLinks = calcLinkCount(m,n,model.getChess());        
        //计算对手在该点四个方向的权值
        for ( short i = 0; i < 4; i++ )
        {
            if ( Math.abs(arrLinks[i]) == 5 )
            {
                p += p2;
            }
            if ( arrLinks[i] == 4 )
            {
                p += p4;
            }
            if ( arrLinks[i] == 3 )
            {
                p += p6;
            }
            if ( arrLinks[i] == 2 )
            {
                p += p8;
            }
        }
        //计算完后恢复该点的原来状态.
        model.setChess(m,n,0);
        arrLinks = null;
        return p;
    }

解决方案 »

  1.   

    package org.javagarden.j2me.fivelink.client;
    /**
     * 游戏的人式智能处理类。
     *
     */
    public class AI
    {    /**
         * 找到最佳下棋点。
         * 基本思路是, 先计算每个点的权值,在权值最高的位置下棋
         * @author Turbo Chen
         * @created 2005-5-11
         */ 
        public static Location findBestChessLocation( Player currentPlayer, FiveLinkModel model)
        {
            //权值数组
            int[][] power = new int[FiveLinkModel.BOARD_SIZE][FiveLinkModel.BOARD_SIZE];
            for ( short i = 0; i < FiveLinkModel.BOARD_SIZE; i++ )
            {
                for ( short j = 0; j < FiveLinkModel.BOARD_SIZE; j++ )
                {
                    // 当已有子时将该点的权值设为-1
                    if ( model.getChess()[i][j] !=0 )
                    {
                        power[i][j] = -1; 
                    }
                    // 否则计算该点权值
                    else
                    {
                        power[i][j] = (short) calcPower(i, j, currentPlayer,model);
                    }
                }
            }
            //计算完所有点的权值后, 再找出其中权值最大的点
            Location bestLoc = calcMaximumPowerLocation(power);
            power = null;
            return bestLoc;    }    /**
         * 找出权值最大点.
         * @param power
         * @return
         */
        private static Location calcMaximumPowerLocation(int[][] power)
        {
            int max = 0;
            short x = 0, y = 0;
            for ( short i = 0; i < FiveLinkModel.BOARD_SIZE; i++ )
            {
                for ( short j = 0; j < FiveLinkModel.BOARD_SIZE; j++ )
                {
                    if ( power[i][j] > max )
                    {
                        x = i;
                        y = j;
                        max = power[i][j];
                    }
                }
            }
            return new Location(x,y);
        }    /**
         * 检查m,n点的权值.<p>
         * 思路是, 假定在m,n位置下棋后,计算4个方向经过该点,同色相连的棋子数量, 不同的数量有不同的
         * 权值,将四个方向上权值相加即为该点的权值.计算完后恢复该点的状态.
         * @param m
         * @param n
         * @param currentPlayer
         * @param model
         * @return
         */
        private static int calcPower(short m, short n,  Player currentPlayer, FiveLinkModel model)
        {
            int p = 0;
            
            //找AI自己的取胜点,
            int p1 = 1000;
            //找AI自己的三个相连的点
            int p3 = 60;
            //找AI自己的两个相连的点
            int p5 = 20;
            //找AI自己的相连的点
            int p7 = 10;        //找对手的取胜点
            int p2 = 85;
            //找对手的三个相连的点
            int p4 = 45;
            //找对手的两个相连的点
            int p6 = 15;
            //找对方的相连的点
            int p8 = 5;
            
            short[] arrLinks = new short[4];
            //如果当是我方下棋, 判断我方所持棋子的颜色, 在该点预下一子, 然后进行后续计算.
            if ( currentPlayer.getChessType()==Player.BLACK )
            {
                //我方是黑子
                model.setChess(m,n,1);
            }else
            {
                //我方是白子
                model.setChess(m,n,-1);
            }
            
            // 计算4个方向上同色相连棋子的数量.
            arrLinks = calcLinkCount(m,n,model.getChess());        //如果m,n是中心点, 将权值加1
            if ( m == FiveLinkModel.BOARD_SIZE/2 && n == FiveLinkModel.BOARD_SIZE/2 )
            {
                p += 1;
            }
            //计算我方在该点四个方向的权值
            for ( short i = 0; i < 4; i++ )
            {
                if ( Math.abs(arrLinks[i]) == 5 )
                {
                    p += p1;
                }
                if ( arrLinks[i] == 4 )
                {
                    p += p3;
                }
                if ( arrLinks[i] == 3 )
                {
                    p += p5;
                }
                if ( arrLinks[i] == 2 )
                {
                    p += p7;
                }
            }
            //如果当是对手方下棋, 判断对方所持棋子的颜色, 在该点预下一子, 然后进行后续计算.
            if ( currentPlayer.getChessType()==1 )
            {
                //如果对方是白子, 
                model.setChess(m,n,-1);
            }else
            {
                //如果对方是黑子,
                model.setChess(m,n,1);
            }        arrLinks = calcLinkCount(m,n,model.getChess());        
            //计算对手在该点四个方向的权值
            for ( short i = 0; i < 4; i++ )
            {
                if ( Math.abs(arrLinks[i]) == 5 )
                {
                    p += p2;
                }
                if ( arrLinks[i] == 4 )
                {
                    p += p4;
                }
                if ( arrLinks[i] == 3 )
                {
                    p += p6;
                }
                if ( arrLinks[i] == 2 )
                {
                    p += p8;
                }
            }
            //计算完后恢复该点的原来状态.
            model.setChess(m,n,0);
            arrLinks = null;
            return p;
        }