五子棋

#include<stdio.h>

#include<stdlib.h>

 

#define RED 1

#define BLACK -1

 

#define RED_RULE 1

#define BLACK_RULE 0

 

#define cusor2logic(i) (i-1)

#define logic2cusor(i) (i+1)

#define clear_vt100  printf("\033[0m");

 

 

int xcusor=logic2cusor(0);

int ycusor=logic2cusor(0);

 

 

enum

{

    WIN,

    EQUEAL,

    CONTINUE

};

 

int rule=0;

 

void save_cusor()

{

    printf("\033[s");

}

 

void recover_cusor()

{

    printf("\033[u");

}

 

void set_cusor( int x, int y )

{

    printf("\033[%d;%dH",y,x);

}

 

void init_five_chess( int (* parr)[20][20])

{

    int i,j;

    for(i=0;i<20;i++)

    {

        for(j=0;j<20;j++)

        {

            (*parr)[i][j]=0;

        }

    }

}

 

void print_five_chess(int (*parr)[20][20] )

{

    system("clear");

    int i,j;

    for(i=0;i<20;i++)

    {

        for(j=0;j<20;j++)

        {

            if( (*parr)[i][j]==0 )

                printf("\033[47m\033[%d;%dH \033[0m",j+1,i+1);

            else if( (*parr)[i][j]==-1 )

                printf("\033[47m\033[30m\033[%d;%dH#\033[0m",j+1,i+1);

            else if( (*parr)[i][j]==1 )

                printf("\033[47m\033[31m\033[%d;%dH@\033[0m",j+1,i+1);

                

        }

    }

 

}

 

int sum_5_row( int * first )

{

    int sum=0;

    int i;

    for(i=0;i<5;i++)

    {

        sum+= first[i];

    }

    /*printf("sum=%d\n",sum);*/

    return sum;

}

 

int sum_5_col( int * first )

{

    int sum=0;

    int i,count;

    for(i=0,count=0;count<5; count++,i+=20)

    {

        sum +=first[i];

    }

    /*printf("sum=%d\n",sum);*/

    return sum;

}

 

int sum_5_right_down( int * first )

{

    int sum=0;

    int i,count;

    for(i=0,count=0;count<5; count++,i+=21)

    {

        sum +=first[i];

    }

    /*printf("sum=%d\n",sum);*/

    return sum;

 

}

 

int sum_5_right_up( int * first )

{

    int sum=0;

    int i,count;

    for(i=0,count=0;count<5; count++,i-=19)

    {

        sum +=first[i];

    }

    return sum;

 

}

 

 

 

//裁判函数,有胜负就返回WIN,平局就返回EQUEAL,还不能判断胜负就返回CONTINUE 

int judge_win( int (*parr)[20][20] )

{

    int i,j;

    int sum;

    //横向判断有没有出现连续五个相同的棋子

    for(i=0;i<20;i++)

    {

        for(j=0;j<16;j++)

        {

            sum =  sum_5_row( &(*parr)[i][j] );

            if( sum==5 || sum==-5 )

                return WIN;

        }

    }

    //纵向判断有没有出现连续五个相同的棋子

    for(i=0;i<20;i++)

    {

        for(j=0;j<16;j++)

        {

            sum =  sum_5_col( &(*parr)[j][i] );

            if( sum==5 || sum==-5 )

                return WIN;

 

        }

    }

 

    //   j=     0   1    2    3   4   5   ....      16  17  18  19

    //i=    0   0   0    0    0   0   0   ....      0   0   0   0      

    //i=    1   1   -1   0    1   0   0   ....      1   1   0   1  

    //i=    2   0   1   -1    0   1   1   ....      1   0   1   0

    //i=    3   1   0    1    1   0   1   ....      0   1   0   1

    //i=    4   

    //i=    5

    //......

    //                                              1   0   1   0

    //                                              0   1   0   1

    //                                              -1  0   1   0

    //i=   19                                       0   1   0   1

 

    //从左上方向右下方的方向上判断有没有出现连续五个相同的棋子,起始为对角线,

    //该循环只判断对角线上方的所有斜线

    int begin_i,begin_j;

    for(begin_i=0,begin_j=0;begin_j<16; begin_j++ )

    {

        for( i=begin_i,j=begin_j;j<16 ;i++,j++ )

        {

            sum = sum_5_right_down( &(*parr)[i][j] );

            if( sum==5 || sum==-5 )

                return WIN;

        }

    }

    //从左上方向右下方的方向上判断有没有出现连续五个相同的棋子,起始为对角线下边的一条线,

    //该循环只判断对角线下方的所有斜线

    for( begin_i=1,begin_j=0; begin_i<16 ; begin_i++ )

    {

        for( i=begin_i,j=begin_j;i<16 ; i++,j++ )

        {

            sum = sum_5_right_down( &(*parr)[i][j] );

            if( sum==5 || sum== -5 )

                return WIN;

        }

    }

    //从左下方向右上方的方向上判断有没有出现连续五个相同的棋子,

    int line_count;

    for( line_count=0,begin_i=4,begin_j=0; 

         begin_j<16  ;

         line_count<15?begin_i++:(line_count==15?0:begin_j++) , line_count++ 

       )

    {

        for( i=begin_i,j=begin_j;i>3 ; i--,j++ )

        {

            sum = sum_5_right_up( &(*parr)[i][j] );

            if( sum == 5 || sum == -5 )

                return WIN;

        }

    }

    int equeal_flag=1;

    for( i=0;i<20;i++ )

    {

        for(j=0;j<20;j++)

        {

            if( (*parr)[i][j]==0 )

            {

                equeal_flag=0;

            }

        }

    }

    if( equeal_flag==1 )

        return EQUEAL;

 

    return CONTINUE; 

}

 

void action_five_chess( int (*parr)[20][20] )

{

    char ch;

    int result;

    while('q' != (ch=getchar() ) )

    {

        if( ch=='a' )

        {   

            if( xcusor>logic2cusor(0) )

            {

                xcusor--;

                printf("\033[1D");

            }

        }

        else if( ch=='d')

        {

            if( xcusor<logic2cusor(19) )

            {

                xcusor++;

                printf("\033[1C");

            }

        }

        else if( ch=='w')

        {

            if( ycusor>logic2cusor(0) )

            {

                ycusor--;

                printf("\033[1A");

            }

        }

        else if( ch=='s')

        {

            if( ycusor<logic2cusor(19) )

            {

                ycusor++;

                printf("\033[1B");

            }

        }

        else if( ch==' ' )//表示有落子动作

        {

            if( (*parr)[cusor2logic(xcusor)][cusor2logic(ycusor)] )

                continue;

            if( rule == RED_RULE )

            {

                (*parr)[cusor2logic(xcusor)][cusor2logic(ycusor)]=RED; 

            }

            else

            {

                (*parr)[cusor2logic(xcusor)][cusor2logic(ycusor)]=BLACK; 

            }

            save_cusor();

            print_five_chess( parr );//打印棋盘 

            set_cusor( xcusor,ycusor );

            /*recover_cusor();*/

 

            result = judge_win(parr);

            

            if( result == WIN )

            {

                printf("%s\n",rule?"红方胜出":"白方胜出");

                break;

            }

            else if( result == EQUEAL )

            {

                printf("平局\n");

            }

            rule =!rule;

        }

    }

}

 

int main(void)

{

    int arr[20][20] ={0};

    system("stty -echo"); 

    system("stty raw"); 

    system("clear");

   

    init_five_chess( &arr );

 

    print_five_chess( &arr );

    printf("\033[0:0H");

    

    action_five_chess( &arr );

 

 

    clear_vt100;

    system("stty cooked");

    system("stty echo");

    return 0;

}

 

转载于:https://www.cnblogs.com/ukennnoblogs/p/4527602.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值