C語言實現(xiàn)五子棋功能全解析_第1頁
C語言實現(xiàn)五子棋功能全解析_第2頁
C語言實現(xiàn)五子棋功能全解析_第3頁
C語言實現(xiàn)五子棋功能全解析_第4頁
C語言實現(xiàn)五子棋功能全解析_第5頁
已閱讀5頁,還剩15頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權,請進行舉報或認領

文檔簡介

第C語言實現(xiàn)五子棋功能全解析目錄1、game.h2、test.c3、game.c4、游戲功能詳解(1)、棋盤初始化(2)、棋盤的打印(3)、玩家下棋(4)、電腦下棋(5)、判斷游戲輸贏(6)、判斷棋盤是否滿了5、AI算法下棋(1)、判斷自己是否會贏(CheckComputer)(2)、對玩家進行攔截(CheckPlayer)(3)、加入AI算法后game.c的改動

1、game.h

game.h:自定義頭文件,用于:

庫函數(shù)頭文件的包含符號與結構的聲明函數(shù)的定義

//防止頭文件被重復包含

#pragmaonce

//頭文件的包含

#includestdio.h

#includestdlib.h

#includetime.h

//符號的定義:使棋盤的大小可以跟著row和col的改變而改變

#defineROW5

#defineCOL5

//函數(shù)的聲明

//棋盤初始化

voidBoardInit(chararr[ROW][COL],introw,intcol);

//打印棋盤

voidBoardPrint(chararr[ROW][COL],introw,intcol);

//玩家下棋

voidPlayerMove(chararr[ROW][COL],introw,intcol);

//電腦下棋

voidComputerMove(chararr[ROW][COL],introw,intcol);

//判斷輸贏

charIsWin(chararr[ROW][COL],introw,intcol);

//判斷棋盤是否滿了

intIsFull(charboard[ROW][COL],introw,intcol);

2、test.c

test.c:用于游戲邏輯的測試

#define_CRT_SECURE_NO_WARNINGS1

//自定義頭文件的包含

#include"game.h"

voidmenu()

printf("================================\n");

printf("=========1.play==========\n");

printf("=========0.exit==========\n");

printf("================================\n");

//游戲邏輯的實現(xiàn)

voidgame()

//定義一個二維數(shù)組來存儲下棋的數(shù)據(jù)

chararr[ROW][COL]={0};

//棋盤初始化

BoardInit(arr,ROW,COL);

//打印棋盤

BoardPrint(arr,ROW,COL);

charch=0;

while(1)

//玩家下棋

PlayerMove(arr,ROW,COL);

//打印棋盤

BoardPrint(arr,ROW,COL);

//判斷輸贏

ch=IsWin(arr,ROW,COL);

if(ch!='C')

break;

//電腦下棋

ComputerMove(arr,ROW,COL);

//打印棋盤

BoardPrint(arr,ROW,COL);

//判斷輸贏

ch=IsWin(arr,ROW,COL);

if(ch!='C')

break;

if(ch=='*')

printf("直接拿下!\n");

elseif(ch=='#')

printf("你竟然打不過人機!\n");

else

printf("平局,得加油啊!\n");

intmain()

intinput=0;

//設置隨機數(shù)種子

srand((unsignedint)time(NULL));

do{

//菜單

menu();

printf("請選擇:

scanf("%d",input);

switch(input){

case1:

//玩游戲

game();

break;

case0:

printf("退出游戲\n");

break;

default:

printf("輸入錯誤,請重新輸入!\n");

break;

}while(input);

return0;

}

3、game.c

game.c:游戲功能的實現(xiàn)

#define_CRT_SECURE_NO_WARNINGS1

//自定義頭文件的包含

#include"game.h"

//函數(shù)的定義

//棋盤初始化

voidBoardInit(chararr[ROW][COL],introw,intcol)

inti=0;

intj=0;

for(i=0;irow;i++)

for(j=0;jcol;j++)

arr[i][j]='';

//打印棋盤

voidBoardPrint(chararr[ROW][COL],introw,intcol)

inti=0;

intj=0;

for(i=0;irow;i++)

//打印分割豎向分割

for(j=0;jcol;j++)

printf("%c",arr[i][j]);

if(jcol-1)

printf("|");

//一行完畢之后打印分隔符

printf("\n");

//打印橫向分割

if(irow-1)//最后一行不打印橫線分隔符

for(j=0;jcol;j++)

printf("---");

if(jcol-1)

printf("|");

//一行完畢之后打印分隔符

printf("\n");

//玩家下棋

voidPlayerMove(chararr[ROW][COL],introw,intcol)

//獲取玩家坐標

intx=0;

inty=0;

printf("玩家下棋\n");

while(1)

printf("請輸入坐標:

scanf("%d%d",x,

//判斷坐標合法性

if((x=1x=row)(y=1y=col))

//把玩家坐標對應數(shù)組下標

x-=1;

y-=1;

//判斷坐標是否被占用

if(arr[x][y]=='')

arr[x][y]='*';//假設玩家為*號

break;

else

printf("該坐標已被占用\n");

else

printf("坐標非法\n");

//電腦下棋

voidComputerMove(chararr[ROW][COL],introw,intcol)

printf("電腦下棋\n");

while(1)

//在主函數(shù)生成種子srand

//隨機生成范圍內(nèi)的坐標

intx=rand()%row;

inty=rand()%col;

//判斷坐標是否被占用

if(arr[x][y]=='')

arr[x][y]='#';//假設電腦為#號

break;

//判斷輸贏

charIsWin(charboard[ROW][COL],introw,intcol)

*約定返回*代表玩家贏

*返回#代表電腦贏

*返回D代表平局

*返回C代表繼續(xù)

inti=0;

intj=0;

//判斷行

for(i=0;irow;i++)

intcount=0;//標記相同棋子的個數(shù)

for(j=0;jcol-1;j++)

if(board[i][j]==board[i][j+1]board[i][j]!='')

count++;

if(count==col-1)//一次判斷有兩個棋子

returnboard[i][j];

//判斷列

for(i=0;icol;i++)

intcount=0;

for(j=0;jrow-1;j++)

if(board[j][i]==board[j+1][i]board[j][i]!='')

count++;

if(count==row-1)

returnboard[j][i];

//判斷兩條斜邊

//第一條

intcount=0;

for(i=0,j=0;irow-1jcol-1;i++,j++)

if(board[i][j]==board[i+1][j+1]board[i][j]!='')

count++;

if(count==row-1)

returnboard[i][j];

//第二條

count=0;//把count重新置為0(易錯)

//注意:這里i+1,j-1,所以i小于row-1,j0,而不是irow,j=0(易錯)

for(i=0,j=col-1;irow-1ji++,j--)

if(board[i][j]==board[i+1][j-1]board[i][j]!='')

count++;

if(count==row-1)

returnboard[i][j];

//判斷棋盤是否滿了

if(IsFull(board,row,col))

return'D';

//如果上述情況都沒有返回,游戲繼續(xù)

return'C';

//判斷棋盤是否滿了

if(IsFull(board,row,col))

return'D';

//如果上述情況都沒有返回,游戲繼續(xù)

return'C';

//判斷棋盤是否滿了

intIsFull(charboard[ROW][COL],introw,intcol)

inti=0;

intj=0;

for(i=0;irow;i++)

for(j=0;jcol;j++)

if(board[i][j]=='')

return0;//有空格就返回0

return1;

}

4、游戲功能詳解

(1)、棋盤初始化

voidBoardInit(chararr[ROW][COL],introw,intcol)

inti=0;

intj=0;

for(i=0;irow;i++)

for(j=0;jcol;j++)

arr[i][j]='';

(2)、棋盤的打印

voidBoardPrint(chararr[ROW][COL],introw,intcol)

inti=0;

intj=0;

for(i=0;irow;i++)

//打印分割豎向分割

for(j=0;jcol;j++)

printf("%c",arr[i][j]);

if(jcol-1)

printf("|");

//一行完畢之后打印分隔符

printf("\n");

//打印橫向分割

if(irow-1)//最后一行不打印橫線分隔符

for(j=0;jcol;j++)

printf("---");

if(jcol-1)

printf("|");

//一行完畢之后打印分隔符

printf("\n");

(3)、玩家下棋

voidPlayerMove(chararr[ROW][COL],introw,intcol)

//獲取玩家坐標

intx=0;

inty=0;

printf("玩家下棋\n");

while(1)

printf("請輸入坐標:

scanf("%d%d",x,

//判斷坐標合法性

if((x=1x=row)(y=1y=col))

//把玩家坐標對應數(shù)組下標

x-=1;

y-=1;

//判斷坐標是否被占用

if(arr[x][y]=='')

arr[x][y]='*';//假設玩家為*號

break;

else

printf("該坐標已被占用\n");

else

printf("坐標非法\n");

(4)、電腦下棋

voidComputerMove(chararr[ROW][COL],introw,intcol)

printf("電腦下棋\n");

while(1)

//在主函數(shù)生成種子srand

//隨機生成范圍內(nèi)的坐標

intx=rand()%row;

inty=rand()%col;

//判斷坐標是否被占用

if(arr[x][y]=='')

arr[x][y]='#';//假設電腦為#號

break;

(5)、判斷游戲輸贏

charIsWin(charboard[ROW][COL],introw,intcol)

*約定返回*代表玩家贏

*返回#代表電腦贏

*返回D代表平局

*返回C代表繼續(xù)

inti=0;

intj=0;

//判斷行

for(i=0;irow;i++)

intcount=0;//標記相同棋子的個數(shù)

for(j=0;jcol-1;j++)

if(board[i][j]==board[i][j+1]board[i][j]!='')

count++;

if(count==col-1)//一次判斷有兩個棋子

returnboard[i][j];

//判斷列

for(i=0;icol;i++)

intcount=0;

for(j=0;jrow-1;j++)

if(board[j][i]==board[j+1][i]board[j][i]!='')

count++;

if(count==row-1)

returnboard[j][i];

//判斷兩條斜邊

//第一條

intcount=0;

for(i=0,j=0;irow-1jcol-1;i++,j++)

if(board[i][j]==board[i+1][j+1]board[i][j]!='')

count++;

if(count==row-1)

returnboard[i][j];

//第二條

count=0;//把count重新置為0(易錯)

//注意:這里i+1,j-1,所以i小于row-1,j0,而不是irow,j=0(易錯)

for(i=0,j=col-1;irow-1ji++,j--)

if(board[i][j]==board[i+1][j-1]board[i][j]!='')

count++;

if(count==row-1)

returnboard[i][j];

//判斷棋盤是否滿了

if(IsFull(board,row,col))

return'D';

//如果上述情況都沒有返回,游戲繼續(xù)

return'C';

//判斷棋盤是否滿了

if(IsFull(board,row,col))

return'D';

//如果上述情況都沒有返回,游戲繼續(xù)

return'C';

}

(6)、判斷棋盤是否滿了

intIsFull(charboard[ROW][COL],introw,intcol)

inti=0;

intj=0;

for(i=0;irow;i++)

for(j=0;jcol;j++)

if(board[i][j]=='')

return0;//有空格就返回0

return1;

}

5、AI算法下棋

大家可以發(fā)現(xiàn),在上面的代碼中,電腦下棋是非常笨拙的,因為電腦產(chǎn)生的坐標是隨機的,即不會攔截玩家,也不會判斷自己,所以這里我們可以設計一個小小的算法來讓電腦變得聰明起來,讓它擁有攔截和判斷功能。具體思路和代碼如下:

(1)、判斷自己是否會贏(CheckComputer)

//電腦檢查自己是否會贏

//約定如果在函數(shù)內(nèi)部成功判斷就返回1

//判斷失敗則返回0

intCheckComputer(charboard[ROW][COL],introw,intcol)

inti=0;

intj=0;

//判斷每一行是否有兩個相連的棋子,如果有,且第三個棋格為空,則落棋

for(i=0;irow;i++)

if(board[i][0]==board[i][1]board[i][0]=='#'board[i][2]=='')

board[i][2]='#';

return1;//成功判斷,返回1

if(board[i][0]==board[i][2]board[i][0]=='#'board[i][1]=='')

board[i][1]='#';

return1;

if(board[i][1]==board[i][2]board[i][1]=='#'board[i][0]=='')

board[i][0]='#';

return1;

//判斷每一列是否有兩個相連的棋子,如果有,且第三個棋格為空,則落棋

for(j=0;jcol;j++)

if(board[0][j]==board[1][j]board[0][j]=='#'board[2][j]=='')

board[2][j]='#';

return1;

if(board[0][j]==board[2][j]board[0][j]=='#'board[1][j]=='')

board[1][j]='#';

return1;

}if(board[1][j]==board[2][j]board[1][j]=='#'board[0][j]=='')

board[0][j]='#';

return1;

//判斷兩條對角線是否有兩個相連的棋子,如果有,且第三個棋格為空,則落棋

//第一條

if(board[0][0]==board[1][1]board[0][0]=='#'board[2][2]=='')

board[2][2]='#';

return1;

if(board[0][0]==board[2][2]board[0][0]=='#'board[1][1]=='')

board[1][1]='#';

return1;

if(board[1][1]==board[2][2]board[1][1]=='#'board[0][0]=='')

board[0][0]='#';

return1;

//第二條

if(board[0][2]==board[1][1]board[0][2]=='#'board[2][0]=='')

board[2][0]='#';

return1;

if(board[0][2]==board[2][0]board[0][2]=='#'board[1][1]=='')

board[1][1]='#';

return1;

if(board[1][1]==board[2][0]board[1][1]=='#'board[0][2]=='')

board[0][2]='#';

return1;

//如果上面都沒返回,說明不符合贏的條件,返回0

return0;

}

(2)、對玩家進行攔截(CheckPlayer)

//電腦檢查玩家是否會贏(邏輯和CheckComputer完全相同)

//約定成功攔截返回1

//無需攔截或者攔截不了返回0

intCheckPlayer(charboard[ROW][COL],introw,intcol)

inti=0;

intj=0;

//判斷每一行是否有兩個相連的棋子,如果有,且第三個棋格為空,則攔截

for(i=0;irow;i++)

if(board[i][0]==board[i][1]board[i][0]=='*'board[i][2]=='')

board[i][2]='#';

return1;//成功攔截,返回1

if(board[i][0]==board[i][2]board[i][0]=='*'board[i][1]=='')

board[i][1]='#';

return1;

if(board[i][1]==board[i][2]board[i][1]=='*'board[i][0]=='')

board[i][0]='#';

return1;

//判斷每一列是否有兩個相連的棋子,如果有,且第三個棋格為空,則攔截

for(j=0;jcol;j++)

if(board[0][j]==board[1][j]board[0][j]=='*'board[2][j]=='')

board[2][j]='#';

return1;

if(board[0][j]==board[2][j]board[0][j]=='*'board[1][j]=='')

board[1][j]='#';

return1;

}if(board[1][j]==board[2][j]board[1][j]=='*'board[0][j]=='')

board[0][j]='#';

return1;

//判斷兩條對角線是否有兩個相連的棋子,如果有,且第三個棋格為空,則攔截

//第一條

if(board[0][0]==board[1][1]board[0][0]=='*'board[2][2]=='')

board[2][2]='#';

return1;

if(board[0][0]==board[2][2]board[0][0]=='*'board[1][1]=='')

board[1][1]='#';

return1;

if(board[1][1]==board[2][2]board[1][1]=='*'board[0][0]=='')

board[0][0]='#';

return1;

//第二條

if(board[0][2]==board[1][1

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
  • 4. 未經(jīng)權益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責。
  • 6. 下載文件中如有侵權或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

評論

0/150

提交評論