C语言实现贪吃蛇(循环链表)
游戏欢迎界面
游戏运行界面
头文件
#include <stdio.h>
#include <windows.h>
#include <time.h>
#include <stdlib.h>
宏定义
#define U 1
#define D 2
#define L 3
#define R 4
#define GKS GetAsyncKeyState
#define uint unsigned int
结构体
typedef struct SNAKE
{
int x;
int y;
struct SNAKE *next;
}snake;
子函数声明
void Pos();
void creatMap();
void gamecircle();
void endgame();
void welcometogame();
void gamestart ();
void pase();
void initsnake();
void cantcrosswall();
void creatfood();
int biteself();
void pause();
void snakemove();
void gamestart_1();
全局变量
uint ends,status,sleeptime=0,a,b;
int score=0,add=10;
///score:总得分 add:每次吃食物得分 ends:游戏结束原因
snake *p,*head,*food,*q,*food_1;
主函数
int main()
{
gamestart();
gamecircle();
endgame();
return 0;
}
游戏欢迎函数
void welcometogame() //游戏欢迎界面///
{
system("title 贪吃蛇大战1.0 ");
system("color 20");
Pos(40,12);
printf("欢迎来到贪吃蛇");
Pos(40,25);
printf("马上就进入游戏");
system("pause"); //暂停运行程序///
system("cls");////一级欢迎页面(清除当前屏幕内容)///
Pos(40,10);
printf("游戏说明");
Pos(40,14);
printf("用↑ ↓ ← →控制蛇的身体");
Pos(40,15);
printf("高难度将能得到更高的分数");
Pos(40,16);
printf("1.普通模式2.中等模式3.难度模式");
Pos(40,18);
printf("请选择游戏模式:");
scanf("%d",&b);
while(1)
{
if(b==1){sleeptime=300;add=10;break;}
else if (b==2){sleeptime=250;add=12;break;}
else if(b==3){sleeptime=150;add=15;break;}
else {printf("请重新输入:");scanf("%d",&b);}
}
system("pause");
system("cls"); ///二级欢迎界面///
}
光标函数(win32 api 函数)
void Pos(int x,int y) ///设置光标位置/////
{
COORD pos;
HANDLE hOutput;
pos.X=x;
pos.Y=y;
hOutput=GetStdHandle(STD_OUTPUT_HANDLE);
SetConsoleCursorPosition(hOutput,pos);
}
地图函数
void creatMap() //创建地图//
{
int i;
for(i=0;i<58;i+=2) //打印上下边框//
{
Pos(i,0);
printf("■");
Pos(i,26);
printf("■");
}
for(i=1;i<26;i++) //打印左右边框//
{
Pos(0,i);
printf("■");
Pos(56,i);
printf("■");
}
}
游戏说明函数
void gamecircle() //游戏说明//
{
Pos(65,17);
printf("1.蛇的身体不能穿墙,也不能咬自己");
Pos(65,19);
printf("2.用↑↓←→控制蛇的身体");
Pos(65,21);
printf("4.ESC:退出游戏 Tab:暂停游戏");
Pos(65,25);
printf("每个食物得分:%d",add);
status=R;
while(1)
{
Pos(65,27);
printf("目前得分为:%d",score);
if(GKS(VK_UP)&&status!=D)status=U;
else if(GKS(VK_DOWN)&&status!=U)status=D;
else if(GKS(VK_LEFT)&&status!=R)status=L;
else if(GKS(VK_RIGHT)&&status!=L)status=R;
else if(GKS(VK_TAB))pause();
else if(GKS(VK_ESCAPE)){ends=3;break;}
Sleep(sleeptime);
snakemove();
}
}
游戏结束函数
void endgame() //游戏结束界面//
{
system("cls");
Pos(28,12);
if(ends==1)
printf("对不起,您撞墙了,游戏结束");
else if(ends==2)
printf("对不起,您自己咬自己了");
else if(ends==3)
printf("您自己结束游戏了");
Pos(28,13);
printf("您最后的得分是:%d\n",score);
Pos(28,17);
printf("1:是继续游戏,2:是直接退出");
Pos(28,19);
printf("请输入:");
scanf("%d",&a);
while(1)
{
if(a==1)
{
system("cls");
gamestart_1();
break;
}
else if(a==2)
{
system("cls");
Pos(40,12);
printf("欢迎下次再玩\n");
system("pause");
exit(0);
}
else
{
printf("请重新输入:");
scanf("%d",&a);
}
}
}
游戏界面初始化函数
void gamestart() //游戏界面初始化//
{
system("mode con cols=100 lines=30");////设置DOS界面的长宽////
welcometogame();
creatMap();
initsnake();
creatfood();
}
蛇身初始化函数
void initsnake() //初始化蛇身//
{
int i=1;
p=(snake*)malloc(sizeof(snake)); //malloc函数返回是一个通用类型指针→
p->x=24; //所以要强制类型转化成snake*(堆内存)
p->y=5;
p->next=NULL;
for(;i<=3;i++)
{
head=(snake*)malloc(sizeof(snake));
head->next=p;
head->x=24+i*2;
head->y=5;
p=head;
}
while(p->next!=NULL)
{
Pos(p->x,p->y);
printf("■");
p=p->next;
}
}
判断穿墙函数
void cantcrosswall() //蛇不能穿墙//
{
if(head->x==0||head->x==56||head->y==0||head->y==26)
{
ends=1;
endgame();
}
}
食物生成函数
void creatfood()///生成食物///
{
srand((unsigned)time(0));//生成种子//
food_1=(snake*)malloc(sizeof(snake));
while(1)//判断是否一个食物节点成功
{
if(food_1==NULL)
{
while(food_1==NULL)
{
free(food_1);
food_1=(snake*)malloc(sizeof(snake));
}
}
else
{
food_1->x=rand()%52+2; //根据不同的种子产生不同的随机数//
if((food_1->x%2)==0)break;
else{
free(food_1);
food_1=(snake*)malloc(sizeof(snake));
}
}
}
food_1->y=rand()%24+1;
q=head;
while(q->next!=NULL)
{
if(food_1->x==q->x&&food_1->y==q->y)
{
free(food_1);
creatfood();
}
q=q->next;
}
Pos(food_1->x,food_1->y);
printf("■");
food=food_1;
}
判断咬自己函数
int biteself() //判断自己是否咬自己//
{
snake*self;
self=head->next;
while(self->next!=NULL)
{
if(self->x==head->x&&self->y==head->y)return 1;
self=self->next;
}
return 0;
}
游戏暂停函数
void pause() //暂停游戏///
{
while(1)
{
Sleep(300);
if(GKS(VK_TAB))break;
}
}
蛇移动函数
void snakemove() //控制蛇的移动//
{
snake*nexthead;
cantcrosswall();
nexthead=(snake*)malloc(sizeof(snake));
if(status==U)//上//
{
nexthead->x=head->x;
nexthead->y=head->y-1;
if(nexthead->x==food->x&&nexthead->y==food->y) //有食物//
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
score+=add;
creatfood();
}
else //没食物//
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
Pos(q->next->x,q->next->y);
printf(" ");
free(q->next);
q->next=NULL;//避免出现野指针(如果不赋值NULL,那q->next访问的是一个垃圾内存)//
}
}
if(status==D) //下//
{
nexthead->x=head->x;
nexthead->y=head->y+1;
if(nexthead->x==food->x&&nexthead->y==food->y)
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
score+=add;
creatfood();
}
else
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
Pos(q->next->x,q->next->y);
printf(" ");
free(q->next);
q->next=NULL;
}
}
if(status==R) //右//
{
nexthead->x=head->x+2;
nexthead->y=head->y;
if(nexthead->x==food->x&&nexthead->y==food->y)
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
score+=add;
creatfood();
}
else
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
Pos(q->next->x,q->next->y);
printf(" ");
free(q->next);
q->next=NULL;
}
}
if(status==L) //左//
{
nexthead->x=head->x-2;
nexthead->y=head->y;
if(nexthead->x==food->x&&nexthead->y==food->y)
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
score+=add;
creatfood();
}
else
{
nexthead->next=head;
head=nexthead;
q=head;
while(q->next->next!=NULL)
{
Pos(q->x,q->y);
printf("■");
q=q->next;
}
Pos(q->next->x,q->next->y);
printf(" ");
free(q->next);
q->next=NULL;
}
}
if(biteself()==1)
{
ends=2;
endgame();
}
}
游戏继续或退出函数
void gamestart_1() //继续游戏或退出游戏//
{ score=0;
creatMap();
initsnake();
creatfood();
gamecircle();
}
代码:https://download.csdn.net/download/qq_37451250/11438746