
#include<graphicsh>
#include<stdlibh>
#define N 200
#define up 0x4800
#define down 0x5000
#define left 0x4b00
#define right 0x4d00
#define esc 0x011b
#define Y 0x1579
#define n 0x316e
int gamespeed; / 游戏速度 /
int i,key,color;
int score=0; / 游戏分数 /
char cai48H[]={
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x04,0x00,0x18,0x00,0x00,0x00,0x0E,0x00,
0x1C,0x00,0x00,0x00,0x1C,0x00,0x1C,0x00,
0x00,0x00,0x20,0x00,0x38,0x00,0x00,0x00,
0x40,0x00,0x78,0x00,0x00,0x01,0x80,0x40,
0x70,0x00,0x00,0x03,0x80,0xC0,0xE0,0x00,
0x00,0x07,0x80,0x80,0xC0,0x00,0x00,0x0E,
0x11,0x81,0xC0,0x00,0x00,0x08,0x61,0x01,
0x80,0x00,0x00,0x00,0x23,0x03,0x04,0x00,
0x00,0x02,0x02,0x00,0x06,0x00,0x00,0x1E,
0x04,0x00,0x0F,0x00,0x00,0x1C,0x1F,0x80,
0x1E,0x00,0x00,0x08,0x3F,0x80,0x3C,0x00,
0x00,0x00,0xFF,0x80,0x38,0x00,0x00,0x03,
0xFF,0x80,0x78,0x00,0x00,0x0F,0xF8,0x00,
0xF0,0x00,0x00,0x7F,0xF0,0x00,0xE0,0x00,
0x03,0xFF,0xFC,0x01,0x80,0x00,0x03,0xC0,
0xFF,0x01,0x03,0x80,0x01,0x01,0xFF,0x00,
0x03,0x80,0x00,0x01,0x3F,0x00,0x07,0x80,
0x00,0x02,0x11,0x00,0x07,0x00,0x00,0x00,
0x10,0x00,0x07,0x00,0x00,0x00,0x10,0x00,
0x0E,0x00,0x00,0x08,0x10,0x00,0x1C,0x00,
0x00,0x30,0x10,0x00,0x18,0x00,0x00,0x70,
0x10,0x00,0x30,0x00,0x01,0xE0,0x10,0x00,
0x70,0x00,0x03,0x80,0x10,0x00,0x60,0x00,
0x00,0x00,0x30,0x00,0xE0,0x00,0x00,0x00,
0xF0,0x01,0xC0,0x00,0x00,0x00,0x70,0x03,
0xC0,0x00,0x00,0x00,0x10,0x07,0x80,0x00,
0x00,0x00,0x00,0x0F,0x00,0x00,0x00,0x00,
0x00,0x1E,0x00,0x00,0x00,0x00,0x00,0x3C,
0x00,0x00,0x00,0x00,0x00,0x70,0x00,0x00,
0x00,0x00,0x01,0xC0,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
};
char she48H[]={
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x04,
0x00,0x00,0x00,0x00,0x00,0x0C,0x00,0x00,
0x00,0x00,0x00,0x0E,0x00,0x00,0x00,0x00,
0x00,0x0E,0x00,0x00,0x00,0x03,0x00,0x07,
0x00,0x00,0x00,0x02,0x00,0x03,0x00,0x00,
0x00,0x02,0x00,0x00,0x00,0x00,0x00,0x02,
0x00,0x00,0xF8,0x00,0x00,0x02,0x00,0x07,
0x86,0x00,0x00,0x02,0x00,0x18,0x03,0x00,
0x00,0x02,0x00,0x00,0x07,0x80,0x00,0x03,
0xF0,0x00,0x07,0x80,0x00,0x0F,0xFC,0x00,
0x0C,0x00,0x00,0x7E,0x3F,0x80,0x00,0x00,
0x01,0xFE,0x1F,0x80,0x00,0x00,0x01,0xE2,
0x39,0x8C,0x00,0x00,0x00,0xC2,0x30,0x08,
0x00,0x00,0x00,0xC2,0x60,0x08,0x00,0x00,
0x00,0xC3,0xE0,0x08,0x60,0x00,0x00,0x7F,
0xE0,0x01,0xE0,0x00,0x00,0x3F,0x80,0x1F,
0xE0,0x00,0x00,0x1E,0x00,0x1F,0x80,0x00,
0x00,0x1E,0x00,0x1F,0x00,0x00,0x00,0x02,
0x38,0x1E,0x00,0x00,0x00,0x07,0xFC,0x1C,
0x00,0x20,0x00,0x07,0xFC,0x18,0x00,0x20,
0x00,0x1F,0x0C,0x10,0x00,0x20,0x00,0x7C,
0x04,0x10,0x00,0x60,0x01,0xF0,0x00,0x10,
0x00,0x60,0x01,0xE0,0x00,0x08,0x00,0xF0,
0x00,0x80,0x00,0x08,0x03,0xF0,0x00,0x00,
0x00,0x07,0xFF,0xF0,0x00,0x00,0x00,0x07,
0xFF,0xF0,0x00,0x00,0x00,0x03,0xFF,0xE0,
0x00,0x00,0x00,0x01,0xFF,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
};
char tun48H[]={
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x0E,0x00,0x00,0x00,0x00,0x00,0x3E,
0x00,0x00,0x00,0x00,0x00,0x7F,0x00,0x00,
0x00,0x00,0x00,0xE0,0x00,0x00,0x00,0x00,
0x03,0xC0,0x00,0x00,0x00,0x00,0x1F,0x00,
0x00,0x00,0x00,0x00,0x7C,0x00,0x00,0x00,
0x00,0x01,0xF8,0x00,0x00,0x00,0x00,0x03,
0xF8,0x00,0x40,0x00,0x00,0x00,0x06,0x07,
0xC0,0x00,0x00,0x00,0x07,0xFF,0xE0,0x00,
0x00,0x00,0x07,0xFF,0xE0,0x00,0x00,0x00,
0x0F,0xFF,0x80,0x00,0x00,0x00,0x7F,0xF8,
0x00,0x00,0x00,0x1F,0xFF,0xF8,0x00,0x00,
0x00,0x1F,0xFF,0xF8,0x00,0x00,0x00,0x1F,
0xFC,0x3C,0x00,0x00,0x00,0x0F,0xF8,0x0E,
0x00,0x00,0x00,0x04,0x70,0x07,0x00,0x00,
0x00,0x00,0x60,0x03,0x80,0x00,0x00,0x00,
0xC0,0x00,0xC0,0x00,0x00,0x01,0x80,0x00,
0x30,0x00,0x00,0x01,0x00,0x3C,0x18,0x00,
0x00,0x02,0x03,0xFF,0x0C,0x00,0x00,0x0C,
0x7F,0xFF,0x8E,0x00,0x00,0x18,0xFF,0xFF,
0xC7,0x80,0x00,0x78,0xFE,0x07,0x87,0xE0,
0x01,0xF0,0x70,0x07,0x03,0xF8,0x07,0xE0,
0x70,0x0E,0x03,0xFE,0x00,0x00,0x38,0x1E,
0x01,0xFE,0x00,0x00,0x3F,0xFE,0x00,0x0C,
0x00,0x00,0x1F,0xFE,0x00,0x00,0x00,0x00,
0x1F,0xFE,0x00,0x00,0x00,0x00,0x0F,0xFE,
0x00,0x00,0x00,0x00,0x04,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
};
char dan48H[]={
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0xFC,0x00,0x00,0x00,0x00,0x07,0xFF,
0x00,0x00,0x00,0x00,0x7F,0xC0,0x80,0x00,
0x00,0x03,0xFF,0x80,0x40,0x00,0x00,0x01,
0xF1,0x80,0x40,0x00,0x00,0x01,0x81,0x80,
0xE0,0x00,0x00,0x00,0x01,0x93,0xF0,0x00,
0x00,0x00,0x01,0xFF,0xF0,0x00,0x00,0x00,
0x21,0xFF,0xF0,0x00,0x00,0x00,0x21,0xF8,
0x00,0x00,0x00,0x00,0x61,0xC0,0x00,0x00,
0x00,0x00,0x61,0x80,0x00,0x00,0x00,0x00,
0xF3,0x00,0x00,0x00,0x00,0x00,0xFF,0x00,
0x00,0x00,0x00,0x01,0xFF,0xC0,0x00,0x00,
0x00,0x03,0xFF,0xF8,0x00,0x00,0x00,0x02,
0x00,0xFC,0x00,0x00,0x00,0x04,0x02,0x1F,
0x00,0x00,0x00,0x08,0x03,0x01,0xC0,0x00,
0x00,0x38,0x03,0x00,0x7C,0x00,0x00,0xF8,
0x07,0xF8,0x3F,0xC0,0x01,0xF0,0x3F,0xFE,
0x3F,0xF8,0x03,0xC1,0xFF,0x0F,0x1F,0xF8,
0x00,0x01,0xE3,0x0F,0x0F,0xF0,0x00,0x01,
0xC3,0x0E,0x00,0x00,0x00,0x01,0x83,0xFC,
0x00,0x00,0x00,0x00,0xC7,0xF8,0x00,0x00,
0x00,0x00,0xFF,0xF8,0x00,0x00,0x00,0x00,
0x7F,0xF0,0x00,0x00,0x00,0x00,0x3F,0x03,
0x80,0x00,0x00,0x00,0x03,0x04,0x00,0x00,
0x00,0x00,0x03,0xF8,0x00,0x00,0x00,0x00,
0x1F,0xF8,0x20,0x00,0x00,0x00,0xFF,0xFF,
0xE0,0x00,0x00,0x07,0xFF,0x81,0xE0,0x00,
0x00,0x07,0xE0,0x00,0xE0,0x00,0x00,0x03,
0x00,0x00,0x60,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
};
char zuo16H[]={
0x18,0xC0,0x18,0xC0,0x19,0x80,0x31,0xFE,
0x33,0xFE,0x76,0xC0,0xF0,0xFC,0xB0,0xFC,
0x30,0xC0,0x30,0xC0,0x30,0xFE,0x30,0xFE,
0x30,0xC0,0x30,0xC0,0x30,0xC0,0x00,0x00,
};
char zhe16H[]={
0x03,0x00,0x03,0x0C,0x1F,0xCC,0x1F,0xD8,
0x03,0x30,0xFF,0xFE,0xFF,0xFE,0x03,0x00,
0x0F,0xF8,0x3F,0xF8,0xEC,0x18,0xCF,0xF8,
0x0C,0x18,0x0F,0xF8,0x0F,0xF8,0x00,0x00,
};
char tian16H[]={
0x00,0x00,0x3F,0xFC,0x3F,0xFC,0x31,0x8C,
0x31,0x8C,0x31,0x8C,0x3F,0xFC,0x3F,0xFC,
0x31,0x8C,0x31,0x8C,0x31,0x8C,0x3F,0xFC,
0x3F,0xFC,0x30,0x0C,0x00,0x00,0x00,0x00,
};
char xue16H[]={
0x33,0x18,0x19,0x98,0x08,0xB0,0x7F,0xFC,
0x7F,0xFC,0x60,0x0C,0x1F,0xF0,0x1F,0xF0,
0x00,0xC0,0x7F,0xFC,0x7F,0xFC,0x01,0x80,
0x01,0x80,0x07,0x80,0x03,0x00,0x00,0x00,
};
char ke16H[]={
0x00,0x00,0x0C,0x18,0xFD,0x98,0xF8,0xD8,
0x18,0x58,0xFE,0x18,0xFE,0x98,0x18,0xD8,
0x3C,0x58,0x7E,0x1E,0xDB,0xFE,0x9B,0xF8,
0x18,0x18,0x18,0x18,0x18,0x18,0x00,0x00,
};
struct Food/定义结构体存储食物的属性/
{
int x; / 食物的坐标 /
int y;
int yes; / 值为0表示屏幕上没有食物,值为1表示屏幕上有食物 /
int color; / 食物颜色 /
}food;
struct Snake/定义结构体存储蛇的属性/
{
int x[N]; / 每一节蛇的坐标 /
int y[N];
int color[N];/存储每一节蛇的颜色/
int node; / 蛇的节数 /
int direction; / 蛇移动的方向 /
int life; / 蛇的生命,如果为1,蛇死,游戏结束 /
}snake;
void init(void)/图形驱动/
{
int driver=DETECT,mode=0;
registerbgidriver(EGAVGA_driver);
initgraph(&driver,&mode,"");
}
void drawmat(char mat,int matsize,int x,int y,int color)/汉字点阵/
{
int i,j,k,m;
m=(matsize-1)/8+1;
for(j=0;j<matsize;j++)
for(i=0;i<m;i++)
for(k=0;k<8;k++)
if(mat[jm+i]&(0x80>>k))
putpixel(x+i8+k,y+j,color);
}
void showword(void)
{/ 调用汉字点阵输出程序,显示标题和作者信息 /
drawmat(cai48H,48,249,-4,7);
drawmat(she48H,48,329,-4,7);
drawmat(tun48H,48,409,-4,7);
drawmat(dan48H,48,489,-4,7);
drawmat(cai48H,48,250,-5,4);
drawmat(she48H,48,330,-5,4);
drawmat(tun48H,48,410,-5,4);
drawmat(dan48H,48,490,-5,4);
/作者 田学科/
drawmat(zuo16H,16,515,465,7);
drawmat(zhe16H,16,530,465,7);
drawmat(tian16H,16,550,465,7);
drawmat(xue16H,16,565,465,7);
drawmat(ke16H,16,580,465,7);
}
void draw(void)/画出四周的墙/
{
if(color==15)
color=0;
setcolor(++color);
setlinestyle(SOLID_LINE,0,1);
for(i=30;i<=600;i+=10)
{
rectangle(i,40,i+10,49);
rectangle(i,451,i+10,460);
}
for(i=40;i<450;i+=10)
{
rectangle(30,i,39,i+10);
rectangle(601,i,610,i+10);
}
}
void prscore(void)
{/ 打印游戏分数 /
char str[10];
setfillstyle(SOLID_FILL,YELLOW);
bar(50,10,200,30);
setcolor(6);
settextstyle(0,0,2);
sprintf(str,"score:%d",score);
outtextxy(55,15,str);
}
void gameover(void)
{
cleardevice(); / 清屏函数 /
for(i=0;i<snakenode;i++)/ 画出蛇死时的位置 /
{
setcolor(snakecolor[i]);
rectangle(snakex[i],snakey[i],snakex[i]+10,snakey[i]+10);
}
prscore(); / 显示分数 /
draw();
showword();
settextstyle(0,0,6);
setcolor(7);
outtextxy(103,203,"GAME OVER");
setcolor(RED);
outtextxy(100,200,"GAME OVER");
}
void gameplay(void)/ 玩游戏的具体过程 /
{
int flag,flag1;
randomize();
prscore();
gamespeed=50000;
foodyes=0;/ foodyes=0表示屏幕上没有食物 /
snakelife=1;/ snakelife=1表示蛇是活着的 /
snakedirection=4;/ 表示蛇的初始方向为向右 /
snakenode=2; / 蛇的初始化为两节 /
snakecolor[0]=2; /两节蛇头初始化为绿色/
snakecolor[1]=2;
snakex[0]=100;snakey[0]=100;
snakex[1]=110;snakey[1]=100;
foodcolor=random(15)+1;
while(1)
{
while(1)
{
if(foodyes==0) / 如果蛇活着 /
{
while(1)
{
flag=1;
foodyes=1;
foodx=random(56)10+40;
foody=random(40)10+50;
for(i=0;i<snakenode;i++)
{
if(foodx==snakex[i]&&foody==snakey[i])
flag=0;
}
if(flag) break;
}
}
if(foodyes)
{
setcolor(foodcolor);
rectangle(foodx,foody,foodx+10,foody+10);
}
for(i=snakenode-1;i>0;i--)
{
snakex[i]=snakex[i-1];
snakey[i]=snakey[i-1];
}
switch(snakedirection)
{
case 1: snakey[0]-=10;break;
case 2: snakey[0]+=10;break;
case 3: snakex[0]-=10;break;
case 4: snakex[0]+=10;break;
}
for(i=3;i<snakenode;i++)
{
if(snakex[i]==snakex[0]&&snakey[i]==snakey[0])
{
gameover();
snakelife=0;
break;
}
}
if(snakex[0]<40||snakex[0]>590||snakey[0]<50||snakey[0]>440)
{
gameover();
snakelife=0;
}
if(snakelife==0)
break;
if(snakex[0]==foodx&&snakey[0]==foody)/蛇吃掉食物/
{
setcolor(0);
rectangle(foodx,foody,foodx+10,foody+10);
snakex[snakenode]=-20;
snakey[snakenode]=-20;
snakecolor[snakenode]=foodcolor;
snakenode++;
foodyes=0;
foodcolor=random(15)+1;
score+=10;
prscore();
if(score%100==0&&score!=0)
{
for(i=0;i<snakenode;i++)/ 画出蛇 /
{
setcolor(snakecolor[i]);
rectangle(snakex[i],snakey[i],snakex[i]+10,snakey[i]+10);
}
sound(200);
delay(50000);delay(50000);delay(50000);
delay(50000);delay(50000);delay(50000);
nosound();
gamespeed-=5000;
draw();
}
else
{
sound(500);
delay(500);
nosound();
}
}
for(i=0;i<snakenode;i++)/ 画出蛇 /
{
setcolor(snakecolor[i]);
rectangle(snakex[i],snakey[i],snakex[i]+10,snakey[i]+10);
}
delay(gamespeed);
delay(gamespeed);
flag1=1;
setcolor(0);
rectangle(snakex[snakenode-1],snakey[snakenode-1],
snakex[snakenode-1]+10,snakey[snakenode-1]+10);
if(kbhit()&&flag1==1)/如果没按有效键就重新开始循环/
{
flag1=0;
key=bioskey(0);
if(key==esc)
exit(0);
else if(key==up&&snakedirection!=2)
snakedirection=1;
else if(key==down&&snakedirection!=1)
snakedirection=2;
else if(key==left&&snakedirection!=4)
snakedirection=3;
else if(key==right&&snakedirection!=3)
snakedirection=4;
}
}
if(snakelife==0)/如果蛇死了就退出循环/
break;
}
}
void main(void)
{
while(1)
{
color=0;
init();
cleardevice();
showword();
draw();
gameplay();
setcolor(15);
settextstyle(0,0,2);
outtextxy(200,400,"CONTINUE(Y/N)");
while(1)
{
key=bioskey(0);
if(key==Y||key==n||key==esc)
break;
}
if(key==n||key==esc)
break;
}
closegraph();
}
用C语言来实现也是一个好玩的事情。这个游戏我写完后放在知乎,竟然点赞的人数超级多。我觉得大家喜欢,一个方面是因为写得简单,大家都能看得懂,一个可扩展性还是非常强的。
我试了说一下这个代码 核心的三个函数
menu();
setup();
draw();
menu用来设置菜单,也就是我们一运行看到的那个。setup用来设置参数,我们需要设置高度和宽度,还有分数,食物的位置。draw也就是画,也就是画整个画面。
还有一个枚举类型 这个结构体用来设置蛇的几个状态,我觉得这个也是面向对象编程的一个思想,把蛇的状态都封装成一个枚举类型。
typedef enum
{
STOP = 0,
LEFT,
RIGHT,
UP,
DOWN
}Direction;
还有
/判断贪吃蛇的长度/
void logic()
这个函数,这个函数应该是整个贪吃蛇的精髓了,要理解代码怎么把蛇给连接起来。用了点巧妙的东西。
来看这里面的关键代码
/把上一个位置记下/
int lastX = tailX[0];
int lastY = tailY[0];
int last2X, last2Y;
/重新获取当前的位置/
tailX[0]=x;
tailY[0]=y;
int i=0;
/遍历整条蛇的长度 把 0 的位置空出来,其余蛇的位置往后面的空间移动/
for(i=1; i ntail;i++)
{
last2X = tailX[i];
last2Y = tailY[i];
tailX[i]=lastX;
tailY[i]=lastY;
lastX = last2X;
lastY = last2Y;
}
lastX lastY 用来存上一次的蛇头的位置。后面的 for 循环,通过tail 蛇的长度,把蛇上个状态给保存到数组tailX tailY里面。
完整代码
#include stdioh
#include stdlibh
#include stdboolh
#include Windowsh
#include timeh
#include conioh /键盘输入获取/
bool gameOver;
bool stop = false;
bool hit = false;
/游戏的边框大小/
const int width = 50;
const int height = 20;
/蛇的坐标,食物的坐标还有分数/
int x,y,fruitX,fruitY,score;
/蛇每个点的坐标/
int tailX[200],tailY[200];
/蛇的默认长度/
int ntail=3;
typedef enum
{
STOP = 0,
LEFT,
RIGHT,
UP,
DOWN
}Direction;
Direction Dir;
/开始菜单/
void menu()
{
int a;
printf( ------------------------------------------------------------------\n
printf( | 贪吃蛇游戏 |\n
printf( | 1) 新游戏 |\n
printf( | 2) 开始边界 |\n
printf( | 3) 退出游戏 |\n
printf( ------------------------------------------------------------------\n
printf( ---- 请输入你的选择:
scanf( %d ,
}
/初始化状态/
void setup()
{
gameOver = false;
/根据当前时间设置“随机数种子”/
srand(time(NULL));
Dir = STOP;
/贪吃蛇的位置,固定在中间/
x= width/2;
y= height/2;
/食物的位置,位置是随机的/
fruitX = rand()%width;
fruitY = rand()%height;
score = 0;
}
/绘制界面/
void draw()
{
if(stop == true)
{
return;
}
system( cls /清除屏幕/
printf( 分数:%d ,score);
printf( \n
/第一行/
int i;
for(i= 0 ;i width+1;i++)
{
printf( -
}
printf( \n
/画中间的画面/
int p;
for(p= 0 ;p height;p++)/高度/
{
int q;
for(q= 0 ;q width;q++)/宽度/
{
/第一行最后已给字符/
if(q==0 || q==width-1)
{
printf( |
}
if(p == fruitY q == fruitX)/食物的随机坐标/
{
printf( O
}
else
{
int k=0;
bool print = false;
/贪吃蛇的长度 默认长度是 3/
for(k=0;k ntail;k++)
{
if(tailX[k]==q tailY[k]==p)
{
printf(
print = true;
}
}
/如果这个位置打印了 就不要打印空格了/
if(!print)
{
printf(
}
}
}
printf( \n
}
/最后一行/
int j;
for(j= 0 ;j width+1;j++)
{
printf( -
}
}
/按键输入控制/
void input()
{
if(_kbhit())
{
/获取键盘的输入字符/
switch(_getch())
{
case 4 :
case 75:/左键/
Dir = LEFT;
hit= true;
break;
case 8 :
case 72:/上键/
Dir = UP;
hit= true;
break;
case 6 :
case 77:/右键/
Dir = RIGHT;
hit= true;
break;
case 2 :
case 80:/向下键盘键 /
Dir = DOWN;
hit= true;
break;
case x :
case 27:/ESE/
gameOver = true;
break;
case 32:/空格 暂停键/
stop = !stop;
break;
}
}
else if(!hit stop == false)/如果没有改变方向/
{
x++;
}
}
/判断贪吃蛇的长度/
void logic()
{
if(stop == true)
{
return;
}
/把上一个位置记下/
int lastX = tailX[0];
int lastY = tailY[0];
int last2X, last2Y;
/重新获取当前的位置/
tailX[0]=x;
tailY[0]=y;
int i=0;
/遍历整条蛇的长度 把 0 的位置空出来,其余蛇的位置往后面的空间移动/
for(i=1; i ntail;i++)
{
last2X = tailX[i];
last2Y = tailY[i];
tailX[i]=lastX;
tailY[i]=lastY;
lastX = last2X;
lastY = last2Y;
}
/根据方向来改变x y 的值/
switch(Dir)
{
case UP:
y--;
break;
case DOWN:
y++;
break;
case LEFT:
x--;
break;
case RIGHT:
x++;
break;
}
if(x 0 || width x || y 0 || height y)
{
gameOver = true;
/清除屏幕/
system( cls
printf( ------------------------------------------------------------------\n
printf( | |\n
printf( | |\n
printf( | 游戏结束 |\n
printf( | |\n
printf( | |\n
printf( ------------------------------------------------------------------\n
}
if(x==fruitX y==fruitY)
{
/吃了一个食物,蛇的长度增加1/
ntail++;
score+=10;
/更新下一个食物的位置/
fruitX = rand()%width;
fruitY = rand()%height;
}
}
int main()
{
#if 0
while(1)
{
printf( %d\n ,_getch());
}
#endif
menu();
setup();
draw();
/循环画贪吃蛇的界面/
while(!gameOver)
{
draw();
input();
logic();
Sleep(70);
}
return 0;
}
上面这段代码直接在Dev C++上面应该是可以运行的,很多人在知乎上私信问我,为什么我的贪吃蛇执行不了呢,可能就是平台不同,少了这个头文件,少了那个头文件,但是你为什么不能跟我一样,用Dev C++呢,轻量级,简单。代码的精髓是什么?我认为精髓一定是思想,不是你写了多少行代码,用了什么高端的IDE。
我自认为我的注释已经写得不错了,所以就没有什么好说明的了吧,有不明白的把代码过一下,至于屏幕刷新这个东西,如果只是用时间刷新就会闪屏,所以出现了一个双缓存,把要显示的东西送到一个buff里面去,另一个buff用来显示,这样就可以保证不会出现闪屏。除了写贪吃蛇,可以用这个方法写其他小程序,挺有意思的。
在知乎上,发起了一个C语言 100 行代码之内实现贪吃蛇的问题。我觉得很不错,里面很多同学的回复都非常赞,特别是叶大神的回复。
0142235ea7197f4e1d7ClTovjpng
学习C/C++编程知识,想要成为一个更加优秀的程序员,或者你学习C/C++的时候有难度,可以来UP主页的C++编程学习圈,里面不仅有学习视频和文件资料,还有更多志同道合的朋友,欢迎初学者和想转行的朋友,和大家一起交流成长会比自己琢磨更快哦! UP也上传了一些C/C++学习的视频教程和C语言基础教程,有兴趣的小伙伴可以看看~ 谢谢阅读!
文章知识点与官方知识档案匹配
C技能树首页概览
115488 人正在系统学习中
点击阅读全文
打开CSDN APP,看更多技术内容
C语言之出圈游戏(详解)
PTA7-5 出圈游戏 用指针实现以下功能:有n个人围成一个圈,顺序排号。从第1个人开始报数(从1到3报数),凡报到3的人退出圈子,问最后留下的是原来的第几号。 (1)编程提示 每三个人离开,置为0;当数到最后一个人时,将指针重新指向第一个人;m表示离开的人数,当m=n-1时,说明只剩下一个人,循环结束。 输入样例: 10 输出样例: 4 上面是题目的要求。 本小白的思路是让n个人形成一个一维数组,每次判断该人是不是要离开, 如果离开,这就不添加到这个一维数组里,并记录下来离开的人数,否则,就在数组里加上这
继续访问
9718 整数因子分解(优先做)
9718 整数因子分解(优先做)Description输入格式输出格式输入样例输出样例 时间限制:1000MS 代码长度限制:10KB 提交次数:0 通过次数:0 题型: 编程题 语言: G++;GCC;VC Description 大于1的正整数 n 都可以分解为 n = x1 x2 … xm, 每个xi为大于1的因子,即1<xi<=n 。 例如:当n=12时,共有8种不同的分解式: 12 = 12 12 = 62 12 = 43 12 = 34 12 = 322 12 =
继续访问
C语言链表——圈中游戏问题(数到3退出)
问题描述: 有n个人围成一圈,从第1个人开始报数1、2、3,每报到3的人退出圈子。使用链表找出最后留下的人。
继续访问
套圈游戏c语言程序设计教程课后答案,概率统计习题带答案
概率论与数理统计习题及题解沈志军 盛子宁第一章 概率论的基本概念1.设事件B A ,及B A 的概率分别为q p ,及r ,试求)(),(),(B A P B A P AB P 及)(AB P2.若C B A ,,相互独立,试证明:C B A ,,亦必相互独立。3.试验E 为掷2颗骰子观察出现的点数。每种结果以),(21x x 记之,其中21,x x 分别表示第一颗、第二颗骰子的点数。设事件}10
继续访问
c语言贪吃蛇设计意义,C语言贪吃蛇设计理念pdf
基于C语言的 “贪吃蛇”游戏的设计与实现摘3功能描述 本游戏主要实现以下几种功能:“贪吃蛇”游戏贪 游 游吃 戏 戏蛇 显 分的
继续访问
热门推荐 一个好玩的小游戏(纯C语言编写)
最近在看知乎是发现了一个这一个专栏 >
C语言贪吃蛇源代码必须经过相应的C/C++编译器编译成EXE文件后才能运行。
由于我们通常使用的 *** 作系统是Windows系统,而在该系统下最长用的C/C++编译器是VC++编译器,目前在大专院校常用的版本还是VC++60
下面就以VC++60来说明编译过程:
1在VC++60中通过“File”菜单下的 “Open”子菜单打开贪吃蛇代码
2在VC++60中通过“Build”菜单下的 “Compile xxxxxx”子菜单编译贪吃蛇代码
3在VC++60中通过“Build”菜单下的 “Execute xxxxexe”子菜单运行贪吃蛇程序
附:在VC++6环境下可运行的C/C++贪吃蛇源代码(无版权,自己编写,欢迎任意修改拷贝)
/C/C++贪吃蛇游戏,zjlj,2015316
/
#define DEBUG 0 //当程序在调试阶段时 DEBUG为 1
#include<iostream>
#include<windowsh>
#include<timeh>
#include<conioh>
using namespace std;
void readini(FILE fphead, int score, char argv[]) //创建或打开一个和运行文件对应的ini文件,读取最高纪录
{
char filename[200],pfilename;
int flag=-1,i;
strcpy(filename,argv[0]);
for(i=0;filename[i]!='\0';i++)
{
if (''==filename[i])flag=1;
}
if(1==flag)
{
filename[i-1]='i';
filename[i-2]='n';
filename[i-3]='i';
}
else
{
filename[i]='';
filename[i+1]='i';
filename[i+2]='n';
filename[i+3]='i';
filename[i+4]='\0';
}
for(;filename[i]!='\\'&&i>=0;i--)pfilename=&filename[i];
if ( (fphead=fopen(pfilename, "rb+"))==NULL)
{
if ( (fphead=fopen(pfilename, "wb+"))==NULL)
{
printf("无法创建或打开\"%s\"文件\n",pfilename);
system("pause");
exit(0);
}
}
else
{
fread(score,sizeof(int),1,fphead);
}
}
void writeini(FILE fphead, int score, char argv[]) //打开一个和运行文件对应的ini文件,写入最高纪录
{
char filename[200],pfilename;
int flag=-1,i;
strcpy(filename,argv[0]);
for(i=0;filename[i]!='\0';i++)
{
if (''==filename[i])flag=1;
}
if(1==flag)
{
filename[i-1]='i';
filename[i-2]='n';
filename[i-3]='i';
}
else
{
filename[i]='';
filename[i+1]='i';
filename[i+2]='n';
filename[i+3]='i';
filename[i+4]='\0';
}
for(;filename[i]!='\\'&&i>=0;i--)pfilename=&filename[i];
if ( (fphead=fopen(pfilename, "wb+"))==NULL)
{
printf("无法写入\"%s\"文件,磁盘写保护!\n",pfilename);
system("pause");
exit(0);
}
else
{
rewind(fphead);
fwrite(score,sizeof(int),1,fphead);
fclose(fphead);
}
}
void gotoxy(int x,int y)//光标定位,光标定位函数SetConsoleCursorPosition是左上角位置是0,0然后向左向下延伸
{
COORD pos;
posX=2y;
posY=x;
SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE),pos);
}
void color(int a)//颜色函数
{
SetConsoleTextAttribute(GetStdHandle(STD_OUTPUT_HANDLE),a);
}
void Refresh(int q[][22], int grade, int gamespeed, int length,int score) // 输出贪吃蛇棋盘
{
int i,j;
for(i=0;i<22;i++)
{
for(j=0;j<22;j++)
{
if(q[i][j]==0)//输出棋盘空白
{
gotoxy(i,j);
color(11);
cout<<"■";
}
if(q[i][j]==1||q[i][j]==2)//输出棋盘墙壁
{
gotoxy(i,j);
color(11);
cout<<"□";
}
if(q[i][j]==3)//输出蛇头
{
gotoxy(i,j);
color(14);
cout<<"★";
}
if(q[i][j]==4)//输出蛇身
{
gotoxy(i,j);
color(12);
cout<<"◆";
}
if(q[i][j]==5)//输出果子
{
gotoxy(i,j);
color(12);
cout<<"●";
}
}
if(i==0) cout << "\t";
if(i==1) cout << "\t等级为:" << grade;//显示等级
if(i==3) cout << "\t自动前进时间";
if(i==4) cout << "\t间隔为:" << gamespeed << "ms";//显示时间
if(i==6) cout << "\t历史最高分为:" << score << "分";
if(i==7) cout << "\t你现在得分为:" << (length+(grade-1)8)10 << "分";
if(i==8) cout << "\t";
if(i==9) cout << "\t游戏说明:";
if(i==10) cout << "\t(1)用小键盘方向键控制";
if(i==11) cout << "\t蛇头运动方向;";
if(i==12) cout << "\t(2)蛇每吃一个果子蛇身";
if(i==13) cout << "\t增加一节;";
if(i==14) cout << "\t(3)蛇咬到自己或碰到墙";
if(i==15) cout << "\t壁游戏结束。";
if(i==18) cout << "\t";
if(i==19) cout << "\tC/C++语言作业:";
if(i==20) cout << "\tzjlj,20150316 ";
}
}
int main(int argc, char argv[]){
int tcsQipan[22][22]; // 贪吃蛇棋盘是一个二维数组(如2222,包括墙壁)
int i,j,score,directiontemp;
FILE fpini;//fpini 信息文件
readini(&fpini, &score, argv);//读取ini文件的最高纪录
if (score<0)//最高成绩小于零设置为零,初建文件会是负数
score=0;
while(1)
{
for(i=1;i<=20;i++)
for(j=1;j<=20;j++)
tcsQipan[i][j]=0; //贪吃蛇棋盘相应坐标标上中间空白部分的标志0
for(i=0;i<=21;i++)
tcsQipan[0][i] = tcsQipan[21][i] = 1; //贪吃蛇棋盘相应坐标标上上下墙壁的标志1
for(i=1;i<=20;i++)
tcsQipan[i][0] = tcsQipan[i][21] = 2; //贪吃蛇棋盘相应坐标标上左右墙壁的标志2
int tcsZuobiao[2][500]; //蛇的坐标数组
for(i=0; i<4; i++)
{
tcsZuobiao[0][i] = 1;//蛇身和蛇头的x坐标
tcsZuobiao[1][i] = i + 1;//蛇身和蛇头的y坐标
}
int head = 3,tail = 0;//标示蛇头和蛇尾的数组偏移量
for(i=1;i<=3;i++)
tcsQipan[1][i]=4; //蛇身
tcsQipan[1][4]=3; //蛇头
int x1, y1; // 随机出果子
srand(time(0));//设置随机种子
do
{
x1=rand()%20+1;
y1=rand()%20+1;
}
while(tcsQipan[x1][y1]!=0);//如果不是在空白处重新出果子
tcsQipan[x1][y1]=5;//贪吃蛇棋盘相应坐标标上果子的标志5
color(12);
cout<<"\n\n\t\t\t\t贪吃蛇游戏即将开始 !"<<endl;//准备开始
long start,starttemp;
int grade = 1, length = 4; //设置初始等级和蛇的初始长度
int gamespeed = 500; //设置初始前进时间间隔
for(i=3;i>=0;i--)
{
start=clock();
while(clock()-start<=1000);
system("cls");
if(i>0)
cout << "\n\n\t\t\t\t进入倒计时:" << i << endl; //倒计时显示
else
Refresh(tcsQipan,grade,gamespeed,length,score); //初始棋盘显示
}
int timeover=1,otherkey=1;//初始化超时时间和按键判断参数
char direction = 77; // 设置初始情况下,向右运动
int x=tcsZuobiao[0][head],y=tcsZuobiao[1][head];//保存蛇头坐标到x,y变量
while(1)//运行一局游戏
{
start = clock();
while((timeover=((starttemp=clock())-start<=gamespeed))&&!kbhit());//如果有键按下或时间超过自动前进时间间隔则终止循环
if(direction==72||direction==80||direction==75 ||direction==77)
directiontemp=direction;//保留上一次方向按键
//starttemp=gamespeed+start-starttemp;//保留停留时间
if(timeover)
{
#if (DEBUG==1)
direction = getch();//调试代码
#else
if((direction =getch())==-32)
direction = getch();
#endif
}
#if (DEBUG==1)//调试代码
start=clock();
while(clock()-start<=2000);
gotoxy(24,4);
cout << "\t按键ASCII代码"<<(int)direction<<" "<<endl;
#endif
if(!(direction==72||direction==80||direction==75 ||direction==77))
{
otherkey=0;// 按键非方向键,otherkey设置为0
}
else
{
otherkey=1;// 按键为方向键,otherkey设置为1
}
if(direction==72 && directiontemp==80)//忽略反方向按键
{
direction=32;
otherkey=0;
//start = clock();
//while(clock()-start<=starttemp);
}
else if(direction==80 && directiontemp==72)
{
direction=32;//设置按键为非方向键
otherkey=0;// 按键为非方向键,otherkey设置为0
// start = clock();
//while(clock()-start<=starttemp);//补偿等待时间
}
else if(direction==75 && directiontemp==77)
{
direction=32;
otherkey=0;
//start = clock();
//while(clock()-start<=starttemp);
}
else if(direction==77 && directiontemp==75)
{
direction=32;
otherkey=0;
//start = clock();
//while(clock()-start<=starttemp);
}
switch(direction)//判断方向键
{
case 72: x= tcsZuobiao[0][head]-1; y= tcsZuobiao[1][head];break; // 向上
case 80: x= tcsZuobiao[0][head]+1; y= tcsZuobiao[1][head];break; // 向下
case 75: x= tcsZuobiao[0][head]; y= tcsZuobiao[1][head]-1;break; // 向左
case 77: x= tcsZuobiao[0][head]; y= tcsZuobiao[1][head]+1;break; // 向右
default: break;
}
if(x==0 || x==21 ||y==0 || y==21) // 蛇头碰到墙壁,结束本局游戏
{
gotoxy(22,12);
cout << "\t游戏已结束!" << endl;
if(score>=(length+(grade-1)8)10)//判断是否破记录
{
gotoxy(10,7);
color(12);
cout << "闯关失败 加油耶!" << endl;
fclose(fpini);//关闭ini文件
}
else
{
gotoxy(10,7);
color(12);
cout << "恭喜您打破记录" << endl;
score=(length+(grade-1)8)10;
writeini(&fpini, &score, argv);//写入ini文件的最高纪录
}
gotoxy(23,12);
cout << "按回车键重新开始,按ESC退出游戏" << endl;//显示的提示
break;//退出该局游戏
}
if(tcsQipan[x][y]!=0&&!(x==x1&&y==y1)&&tcsQipan[x][y]!=3) // 蛇头碰到蛇身,结束本局游戏
{
gotoxy(22,12);
cout << "\t游戏已结束!" << endl;
if(score>=(length+(grade-1)8)10)//判断是否破记录
{
gotoxy(10,7);
color(12);
cout << "闯关失败 加油耶!" << endl;
fclose(fpini);//关闭ini文件
}
else
{
gotoxy(10,7);
color(12);
cout << "恭喜您打破记录" << endl;
score=(length+(grade-1)8)10;
writeini(&fpini, &score, argv);//写入ini文件的最高纪录
}
gotoxy(23,12);
cout << "按回车键重新开始,按ESC退出游戏" << endl;//显示的提示
break;//退出该局游戏
}
/
游戏运行时的核心算法开始
/
if(x==x1 && y==y1) // 吃果子,长度加1
{
length ++;
if(length>=8)//长度大于等于8重新计算长度,等级加1
{
length -= 8;//重新计算长度
grade ++;//等级加1
if(gamespeed>50)//控制最快速度为50
gamespeed = 550 - grade 50; // 改变自动前进时间间隔
}
tcsQipan[x][y]= 3;//贪吃蛇棋盘相应坐标现在蛇头标志改为蛇头标志3
tcsQipan[tcsZuobiao[0][head]][tcsZuobiao[1][head]] = 4;//贪吃蛇棋盘相应坐标原来蛇头标志改为蛇身标志4
head = (head+1)%400;//防止数组越界
tcsZuobiao[0][head] = x;//蛇头的x坐标
tcsZuobiao[1][head] = y;//蛇头的y坐标
do//随机出果子
{
x1=rand()%20+1;
y1=rand()%20+1;
}
while(tcsQipan[x1][y1]!=0);//如果不是在空白处重新出果子
tcsQipan[x1][y1]=5;//贪吃蛇棋盘相应坐标标上果子的标志5
gotoxy(22,12);
cout << "\t游戏进行中!" << endl;
Refresh(tcsQipan,grade,gamespeed,length,score);
}
else // 不吃果子
{
if(otherkey)
{
tcsQipan [tcsZuobiao[0][tail]][tcsZuobiao[1][tail]]=0;
tail=(tail+1)%400;//防止数组越界
tcsQipan [tcsZuobiao[0][head]][tcsZuobiao[1][head]]=4;
head=(head+1)%400;//防止数组越界
tcsZuobiao[0][head]=x;//蛇头的x坐标
tcsZuobiao[1][head]=y;//蛇头的y坐标
tcsQipan[tcsZuobiao[0][head]][tcsZuobiao[1][head]]=3;
gotoxy(22,12);
cout << "\t游戏进行中!" << endl;
Refresh(tcsQipan,grade,gamespeed,length,score);
}
else
{
gotoxy(22,12);
cout << "\t游戏暂停中!" << endl;
}
}
/
游戏运行时的核心算法结束
/
}
while(1)
{
while(!kbhit());
if((direction =getch())==13)//按回车键开始下一局
break;
if(direction ==27)//按ESC退出游戏
exit(0);
}
system("cls");//清除屏幕重新开始
}
return 0;
}
以上就是关于贪吃蛇 C语言 简易程序设计全部的内容,包括:贪吃蛇 C语言 简易程序设计、利用解释型语言编写的贪吃蛇程序什么意思、c语言贪吃蛇源代码怎么用等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!
欢迎分享,转载请注明来源:内存溢出
微信扫一扫
支付宝扫一扫
评论列表(0条)