C語(yǔ)言實(shí)現(xiàn)鏈表貪吃蛇
本文實(shí)例為大家分享了C語(yǔ)言實(shí)現(xiàn)貪吃蛇的具體代碼,供大家參考,具體內(nèi)容如下
用C語(yǔ)言鏈表寫(xiě)的貪吃蛇(程序設(shè)計(jì)時(shí)做的,做的不好大佬勿噴)
借助游戲內(nèi)容分析貪吃蛇所需的功能主要包括這幾塊:
1.移動(dòng)光標(biāo)模塊
2.打印地圖模塊和基本規(guī)則信息
讀取最高分文件
3.打印初始蛇模塊
打印時(shí)給予蛇的初始移動(dòng)方向
4.產(chǎn)生食物模塊
1)、保證食物在地圖內(nèi)產(chǎn)生
2)、保證食物不能出現(xiàn)在蛇體
5.蛇的生命狀態(tài)判斷模塊
1)、撞墻導(dǎo)致死亡
2)、頭撞身體部位死亡
6.運(yùn)行模塊
1)、讓蛇移動(dòng)
2)、根據(jù)按鍵來(lái)改變蛇的移動(dòng)方向
3)、對(duì)待分?jǐn)?shù)的增加游戲難度的增加
4)、蛇在吃食物后分?jǐn)?shù)的增加
7.結(jié)束模塊
在遇到撞墻或者撞自己部位死亡時(shí)結(jié)束程序,并進(jìn)行分?jǐn)?shù)與歷史最高分作比較,最終達(dá)到最高分的更新
以下為代碼
#include <stdlib.h> #include <stdio.h> #include <conio.h>//控制臺(tái)輸入和輸出 #include <windows.h>//窗口函數(shù) #include <time.h> #define W 1//蛇的運(yùn)動(dòng)方向W:上 S:下 A: 左 D:右 #define S 2 #define A 3 #define D 4 /* 定義全局變量 */ typedef struct{ int x; int y; }place;//定義坐標(biāo)結(jié)構(gòu)體 typedef struct ZB{ place data; struct ZB *next; }snake;//定義蛇的鏈表 /* 定義全局鏈表 */ snake *head,*p,*q,*h;// place food;//定義食物坐標(biāo) int score=0,bestscore,game_flag=0,ch,sleep=400;//定義得分score死亡判斷game_flag方向判斷ch蛇的速度sleep /* 函數(shù)聲明 */ void gotoxy(int x,int y);//定位光標(biāo) void map_creat();//運(yùn)用定位函數(shù)打印地圖 void ini_snack();//隨機(jī)產(chǎn)生蛇 void cre_food();//隨機(jī)產(chǎn)生食物 void live_jud_1();//判斷自己是否撞墻死亡 void live_jud_2();//判斷自己是否撞到自己 void move();//蛇的移動(dòng) void rungame();//游戲運(yùn)行 void gameover();//游戲結(jié)束界面 void changch();//改變方向 int color(int c);//改顏色函數(shù) /* 構(gòu)建定位函數(shù) */ int color(int c) { SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE),c); //更改文字顏色 return 0; } void gotoxy(int x,int y)//定位光標(biāo) { COORD pos; HANDLE handle=GetStdHandle(STD_OUTPUT_HANDLE); pos.X=x; pos.Y=y; SetConsoleCursorPosition(handle,pos); } /* 打印地圖 */ void map_creat()//運(yùn)用定位函數(shù)打印地圖 { FILE *fp;//創(chuàng)建一個(gè)記錄最高分的文件 fp=fopen("score.1","r"); fscanf(fp,"%d",&bestscore);//讀取最高分 fclose(fp); gotoxy(54,26); printf("Your Best Score : %d\t", bestscore);//打印出最高分 int i,j; for(i=0;i<48;i++) { gotoxy(i,0); printf("#"); color(6); gotoxy(i,26); printf("#"); color(6); } for(j=0;j<26;j++) { gotoxy(0,j); printf("#"); color(6); gotoxy(48,j); printf("#"); color(6); } gotoxy(54,10); printf("游戲規(guī)則:"); gotoxy(54,12); printf("向上移動(dòng):↑\n"); gotoxy(54,14); printf("向下移動(dòng):↓\n"); gotoxy(54,16); printf("向左移動(dòng):←\n"); gotoxy(54,18); printf("向右移動(dòng):→\n"); gotoxy(54,20); printf("吃一個(gè)食物分?jǐn)?shù)加10"); gotoxy(54,22); printf("按空格鍵暫停游戲"); gotoxy(54,24); printf("按ESC直接結(jié)束游戲"); } /* 構(gòu)建初始蛇 */ void ini_snack()//產(chǎn)生蛇 { int i; /* 采用尾插法構(gòu)建蛇的鏈表初始長(zhǎng)度設(shè)為二 */ head=(snake *)malloc(sizeof(snake)); head->data.x=48/2; head->data.y=26/2; head->next=NULL; h=head; for(i=1;i<=2;i++) { p=(snake *)malloc(sizeof(snake)); p->data.x=48/2+i; p->data.y=26/2; h->next=p; h=p; } p->next=NULL; /* 將蛇打印出來(lái) */ h=head; while(h!=NULL) { gotoxy(h->data.x,h->data.y); color(5); printf("@"); h=h->next; } ch=W;//蛇的初始方向 } /* 隨機(jī)產(chǎn)生食物 */ void cre_food()//隨機(jī)產(chǎn)生食物 { srand((unsigned)time(NULL));//為了防止每次產(chǎn)生的隨機(jī)數(shù)相同,種子設(shè)置為time /* 隨機(jī)產(chǎn)生食物 */ food.x=rand()%(48-2)+1; food.y=rand()%(26-2)+1; while(p!=NULL) { /* 判斷食物是否與蛇重合,如果重合重新產(chǎn)生 */ if(p->data.x==food.x&&p->data.y==food.y) cre_food(); p=p->next; } gotoxy(food.x,food.y); color(1); printf("$");//打印食物 } /* 判斷是否死亡 */ void live_jud_1()//判斷自己是否撞墻死亡 { if(head->data.x==0||head->data.x==48||head->data.y==0||head->data.y==26)//撞墻 { game_flag=1; gameover(); } } void live_jud_2()//判斷自己是否撞到自己 { q=head->next; while(q!=NULL) { if(head->data.x==q->data.x&&head->data.y==q->data.y)//撞自己 { { game_flag=2; gameover(); } break; } q=q->next; } } /* 游戲進(jìn)行界面 */ void move() { snake *l; live_jud_1(); l=(snake *)malloc(sizeof(snake)); /* 構(gòu)建一個(gè)新的節(jié)點(diǎn)通,過(guò)新節(jié)點(diǎn)來(lái)表示下一次頭節(jié)點(diǎn)所在的位置 將新節(jié)點(diǎn)當(dāng)作移動(dòng)后的頭節(jié)點(diǎn) 如果新頭節(jié)點(diǎn)的坐標(biāo)等于食物的坐標(biāo)得分加10,食物的標(biāo)志變?yōu)? 因?yàn)樯叩逆湵黹L(zhǎng)度加了一,如果是移動(dòng)的話(huà)找出尾節(jié)點(diǎn)并打印出 然后刪掉該尾節(jié)點(diǎn) 如果吃到了食物就直接將蛇打印出來(lái) */ if(ch==W) { l->data.x=head->data.x; l->data.y=head->data.y-1; if(l->data.x==food.x&&l->data.y==food.y) { l->next=head; head=l; q=head; while(q!=NULL)//將蛇重新打印一邊 { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } score+=10; cre_food();//構(gòu)建新的食物 } else { l->next=head; head=l; q=head; while(q->next->next!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } gotoxy(q->next->data.x,q->next->data.y); printf(" ");//將蛇尾去掉 free(q->next); q->next=NULL; } } if(ch==A) { l->data.x=head->data.x-1; l->data.y=head->data.y; if(l->data.x==food.x&&l->data.y==food.y) { l->next=head; head=l; q=head; while(q!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } score+=10; cre_food(); } else { l->next=head; head=l; q=head; while(q->next->next!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } gotoxy(q->next->data.x,q->next->data.y); printf(" "); free(q->next); q->next=NULL; } } if(ch==S) { l->data.x=head->data.x; l->data.y=head->data.y+1; if(l->data.x==food.x&&l->data.y==food.y) { l->next=head; head=l; q=head; while(q!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } score+=10; cre_food(); } else { l->next=head; head=l; q=head; while(q->next->next!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } gotoxy(q->next->data.x,q->next->data.y); printf(" "); free(q->next); q->next=NULL; } } if(ch==D) { l->data.x=head->data.x+1; l->data.y=head->data.y; if(l->data.x==food.x&&l->data.y==food.y) { l->next=head; head=l; q=head; while(q!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } score+=10; cre_food(); } else { l->next=head; head=l; q=head; while(q->next->next!=NULL) { gotoxy(q->data.x,q->data.y); color(5); printf("@"); q=q->next; } gotoxy(q->next->data.x,q->next->data.y); printf(" "); free(q->next); q->next=NULL; } } live_jud_2();//判斷是否撞自己死亡 } void rungame()//運(yùn)行游戲 { while(1) { gotoxy(54,8); printf("Your Score:%d",score); /* 以下確保不能向上運(yùn)動(dòng)時(shí)改方向?yàn)橄蛳碌惹闆r */ if(GetAsyncKeyState(VK_UP)&&ch!=S) ch=W; else if(GetAsyncKeyState(VK_DOWN)&&ch!=W) ch=S; else if(GetAsyncKeyState(VK_LEFT)&&ch!=D) ch=A; else if(GetAsyncKeyState(VK_RIGHT)&&ch!=A) ch=D; /* 根據(jù)分?jǐn)?shù)和Sleep函數(shù)來(lái)確定游戲難度 */ if(score>=50&&score<100) sleep=300; else if(score>=100&&score<300) sleep=250; else if(score>=300) sleep=200; if(GetAsyncKeyState(VK_SPACE))//輸入space暫停游戲 { while(1) { Sleep(300); if(GetAsyncKeyState(VK_SPACE)) break; } } else if (GetAsyncKeyState(VK_ESCAPE))//輸入ESC直接結(jié)束游戲 { game_flag=3; gameover(); } Sleep(sleep); move(); } } /* 游戲結(jié)束界面 */ void gameover()//游戲結(jié)束界面 { FILE *fp; system("cls");//清屏 gotoxy(48/2,26/2-2); printf("\tGame Over!!!");//打印出游戲結(jié)束界面 gotoxy(48/2,26/2); if(game_flag==1) printf("\t你撞墻了?。。n"); else if(game_flag==2) printf("\t傻孩子!你不能吃你自己?。?!\n"); else if(game_flag==3) printf("\t您已結(jié)束游戲!"); gotoxy(48/2,26/2+2); printf("\tYour score:%d\n",score);//打印出得到的分?jǐn)?shù) if(score>bestscore)//如果此次游戲分?jǐn)?shù)大于以前最高分 { fp=fopen("score.1","w"); fprintf(fp,"%d",score);//將此次分?jǐn)?shù)保存在最高分文件里 fclose(fp); } system("pause"); exit(0); } /* 主函數(shù) */ int main() { system("color 9"); map_creat(); ini_snack(); cre_food(); rungame(); return 0; }
更多有趣的經(jīng)典小游戲?qū)崿F(xiàn)專(zhuān)題,分享給大家:
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
- C語(yǔ)言實(shí)現(xiàn)簡(jiǎn)單貪吃蛇小游戲
- C語(yǔ)言開(kāi)發(fā)實(shí)現(xiàn)貪吃蛇游戲
- C語(yǔ)言實(shí)現(xiàn)貪吃蛇游戲設(shè)計(jì)
- C語(yǔ)言實(shí)現(xiàn)貪吃蛇游戲(單人版)
- C語(yǔ)言實(shí)現(xiàn)貪吃蛇游戲(命令行)
- C語(yǔ)言實(shí)現(xiàn)貪吃蛇小游戲
- C語(yǔ)言手把手教你實(shí)現(xiàn)貪吃蛇AI(下)
- C語(yǔ)言手把手教你實(shí)現(xiàn)貪吃蛇AI(中)
- 基于C語(yǔ)言實(shí)現(xiàn)的貪吃蛇游戲完整實(shí)例代碼
- C語(yǔ)言實(shí)現(xiàn)貪吃蛇游戲代碼
相關(guān)文章
C++ explicit關(guān)鍵字的應(yīng)用方法詳細(xì)講解
C++ explicit關(guān)鍵字用來(lái)修飾類(lèi)的構(gòu)造函數(shù),表明該構(gòu)造函數(shù)是顯式的,既然有"顯式"那么必然就有"隱式",那么什么是顯示而什么又是隱式的呢?下面就讓我們一起來(lái)看看這方面的知識(shí)吧2013-09-09C語(yǔ)言實(shí)現(xiàn)飛機(jī)訂票系統(tǒng)
這篇文章主要為大家詳細(xì)介紹了C語(yǔ)言實(shí)現(xiàn)飛機(jī)訂票系統(tǒng),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2019-12-12C語(yǔ)言中無(wú)符號(hào)數(shù)和有符號(hào)數(shù)之間的運(yùn)算
C語(yǔ)言中有符號(hào)數(shù)和無(wú)符號(hào)數(shù)進(jìn)行運(yùn)算默認(rèn)會(huì)將有符號(hào)數(shù)看成無(wú)符號(hào)數(shù)進(jìn)行運(yùn)算,其中算術(shù)運(yùn)算默認(rèn)返回?zé)o符號(hào)數(shù),邏輯運(yùn)算當(dāng)然是返回0或1了。下面通過(guò)一個(gè)例子給大家分享C語(yǔ)言中無(wú)符號(hào)數(shù)和有符號(hào)數(shù)之間的運(yùn)算,一起看看吧2017-09-09vscode配置遠(yuǎn)程開(kāi)發(fā)環(huán)境并遠(yuǎn)程調(diào)試運(yùn)行C++代碼的教程
這篇文章主要介紹了vscode配置遠(yuǎn)程開(kāi)發(fā)環(huán)境并遠(yuǎn)程調(diào)試運(yùn)行C++代碼的教程,本文通過(guò)截圖實(shí)例相結(jié)合給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-04-04C++異步操作future和aysnc與function和bind
這篇文章主要介紹了C++異步操作future和aysnc與function和bind,文章圍繞主題展開(kāi)詳細(xì)的內(nèi)容介紹,具有一定的參考價(jià)值,需要的小伙伴可以參考一下2022-09-09