五子棋游戏程序(较高难度+有加分)(设计分值:20-30分)
应用C语言编写程序,可以在计算机上实现二人对弈五子棋功能。
功能要求:
(1)欢迎界面生成、游戏界面生成;
(2)光标移动和落子显示;
(3)判断胜负;
(4)综合应用结构体、数组、按键处理和图形编程等编程方法。
§10.2算法设计
§10.4程序分析
#include<stdio.h>
#include<windows.h>
#include<conio.h>
int qipan[21][21];
int color=0;//0表示黑棋(圆圈),1表示白棋
int iTemp = 0,jTemp = 0,countTemp = 0;
int colorFlag = 0;
void print()
{
int i,j;
for(i=1;i<=20;i++)
{
//第一行
if(i==1)
{
//第一列
if(qipan[i-1][0]==1)
printf("●");
if(qipan[i-1][0]==0)
printf("○");
if(qipan[i-1][0]==2)
printf("┌ ");
//第2-19列
for(j=2;j<=19;j++)
{
if(qipan[i-1][j-1]==1)
printf("●");
if(qipan[i-1][j-1]==0)
printf("○");
if(qipan[i-1][j-1]==2)
printf("┬ ");
}
//第20列
if(qipan[i-1][j-1]==1)
printf("●");
if(qipan[i-1][j-1]==0)
printf("○");
if(qipan[i-1][j-1]==2)
printf("┐ ");
printf("\n");
}
//第2-19行
if(i<=19 && i>=2)
{
//第一列
if(qipan[i-1][0]==1)
printf("●");
if(qipan[i-1][0]==0)
printf("○");
if(qipan[i-1][0]==2)
printf("├ ");
//第2-19列
for(j=2;j<=19;j++)
{
if(qipan[i-1][j-1]==1)
printf("●");
if(qipan[i-1][j-1]==0)
printf("○");
if(qipan[i-1][j-1]==2)
printf("┼ ");
}
//第20列
if(qipan[i-1][j-1]==1)
printf("●");
if(qipan[i-1][j-1]==0)
printf("○");
if(qipan[i-1][j-1]==2)
printf("┤ ");
printf("\n");
}
//第20行
if(i==20)
{
if(qipan[i-1][0]==1)
printf("●");
if(qipan[i-1][0]==0)
printf("○");
if(qipan[i-1][0]==2)
printf("└ ");
for(j=2;j<=19;j++)
{
if(qipan[i-1][j-1]==1)
printf("●");
if(qipan[i-1][j-1]==0)
printf("○");
if(qipan[i-1][j-1]==2)
printf("┴ ");
}
if(qipan[i-1][j-1]==1)
printf("●");
if(qipan[i-1][j-1]==0)
printf("○");
if(qipan[i-1][j-1]==2)
printf("┘ ");
printf("\n");
}
}
}
void gotoxy(HANDLE hout,int x,int y)
{
COORD pos;
pos.X=x;
pos.Y=y;
SetConsoleCursorPosition(hout,pos);
}
void win()
{
int i,j;
for(i=0;i<20;i++)
{
for(j=0;j<20;j++)
{
//如果检测到该有棋子,则检查与该棋子有关的是否可以赢
if(2 != qipan[i][j] )
{
colorFlag = qipan[i][j];
countTemp = 1;
iTemp = i;
jTemp = j;
//该棋子横向上是否可以赢
while((++jTemp<20 )&&(countTemp!=5 ))
{
if(colorFlag == qipan[i][jTemp])
{
countTemp++;
if(countTemp==5)
{
if(colorFlag==0)
{
printf("黑棋赢了!\a\n");
}
else if(colorFlag==1)
{
printf("白棋赢了!\a\n");
}
exit(0);
}
}
else
{
countTemp = 0;
break;
}
}
//纵向可以赢
iTemp = i;
jTemp = j;
countTemp = 1;
while((++iTemp<20 )&&(countTemp!=5))
{
if(colorFlag==qipan[iTemp][j])
{
countTemp++;
if( countTemp==5)
{
if(colorFlag==0)
{
printf("黑棋赢了!\a\n");
}
else if(colorFlag==1)
{
printf("白棋赢了!\a\n");
}
exit(0);
}
}
else
{
countTemp= 0;
break;
}
}
//斜向,从左上到右下方向检查
iTemp = i;
jTemp = j;
countTemp = 1;
while((++iTemp<20 )&&(++jTemp<20 )&&(countTemp!=5))
{
if(colorFlag == qipan[iTemp][jTemp])
{
countTemp++;
if(countTemp==5)
{
if(colorFlag==0)
{
printf("黑棋赢了!\a\n");
}
else if(colorFlag ==1)
{
printf("白棋赢了!\a\n");
}
exit(0);
}
}
else
{
countTemp = 0;
break;
}
}
//斜向,从右上到左下方向检查
iTemp = i;
jTemp = j;
countTemp = 1;
while((++iTemp>=0 )&&(--jTemp>=0)&&(countTemp!=5))
{
if(colorFlag == qipan[iTemp][jTemp])
{
countTemp++;
if(countTemp==5)
{
if(colorFlag==0)
{
printf("黑棋赢了!\a\n");
}
else if(colorFlag==1)
{
printf("白棋赢了!\a\n");
}
exit(0);
}
}
else
{
countTemp = 0;
break;
}
}
}
}
}
}
void getxy(HANDLE hout,int*i,int*j)
{
int ch;
int m,n;
do
{
ch=0;
if (kbhit())
{
ch=getch();//getch() 接受任意键的输入,不用按回车就返回,返回值是输入值的ascll码
}
switch(ch)
{
case 72: *i-=1; break;//上
case 80: *i+=1; break;//下
case 75: *j-=1; break;//左
case 77: *j+=1; break;//右
}
if (*i<0) *i=20+*i;
if (*i>19) *i=20-*i;
if (*j<0) *j=20+*j;
if (*j>19) *j=20-*j;
m=*j;n=*i;
gotoxy(hout,m*2,n);
}while (ch!=13);
}
int main()
{
HANDLE hout=GetStdHandle(STD_OUTPUT_HANDLE);
int i=0,j=0;
int iTemp = 0,jTemp = 0,countTemp = 0;
int colorFlag = 0;
char op;
for(i=0;i<21;i++)
for(j=0;j<21;j++)
qipan[i][j]=2;
while(1)
{
gotoxy(hout,0,0);
print();
gotoxy(hout,49,1);
if (!color)
{
printf("黑棋下\n");
}
else
{
printf("白棋下\n");
}
gotoxy(hout,41,2);
i=0;
j=0;
getxy(hout,&i,&j);
i++;
j++;
if((2 != qipan[i-1][j-1]))
{
gotoxy(hout,41,2);
printf("提示:该位置已经有棋子了! \a \n");
fflush(stdin);
continue;
}
qipan[i-1][j-1]=color;//将该位置棋子属性给棋盘
color=(color+1)%2;//获取棋盘棋子属性
//根据棋盘对应位置属性,绘制最新状态的棋盘
gotoxy(hout,0,0);
print();
win();
system("cls");
}
return 0;
}
§10.5效果截图
1.开始
2.胜利
3.已有子