博主初学c,简单的做了一个贪吃蛇,在此记录下我做贪吃蛇的过程,不足之处望各位博友见谅。
因为博主才疏学浅,所以博主这次只用数组来完成这个程序。
话不多说,直接上码。
主函数:
int main()
{
int dir=UP;
while (1){
print_game();
dir=get_dir(dir);
move_snake(dir);
if (!isalive())
break;
}
printf("Game Over\n");
}
正如博客名所示,博主只用数组。那么我们用一个二维数组char map[17][17]来表示地图,用一维数组unsigned char snake[15]来表示蛇的坐标。这里之所以用char是因为本着能省则省的原则,我们这是一个17*17大小的小游戏,char足够了。
#include <stdio.h>
#include <conio.h>
#include <stdlib.h>
#include <windows.h>
#include <time.h>
#define UP 72
#define DOWN 80
#define LEFT 75
#define RIGHT 77
#define SNAKE 1
#define FOOD 2
#define BAR 3
char map[17][17] = { 0 };
unsigned char snake[50] = { 77 };
unsigned char food = 68;
char len = 1;
void tran(unsigned char num,unsigned char *x, unsigned char *y)
{
*x = num >> 4;
*y = (unsigned char)(num << 4) >> 4;
}
碰到被调用函数需要返回两个以上参数的时候,应该像上述函数一样,将要返回的值写成指针参数。
接下来,让我们把主函数里调用的函数一一填上。
void print_game(void){
int i, j;
for (i = 0; i<17; i++) {
for (j = 0; j<17; j++) {
if (map[i][j] == 0)
putchar(' ');
else if (map[i][j] == SNAKE)
putchar('*');
else if (map[i][j] == BAR)
putchar('#');
else if(map[i][j]==FOOD)
putchar('!');
}
putchar('\n');
}
Sleep(100);
system("cls");
}
int get_dir(int old_dir)
{
int new_dir = old_dir;
if (_kbhit()) {
_getch();
new_dir = _getch();
if (len > 1 && (abs(new_dir - old_dir) == 2 || abs(new_dir - old_dir) == 8))
new_dir = old_dir;
}
return new_dir;
}
接下来是移动蛇身的函数(游戏的大部分内容都在其中):
void move_snake(int dir)
{
int last = snake[0],current;
int i, j;
int grow=0;
unsigned char x, y,fx,fy;
tran(food, &fx, &fy);
tran(snake[0], &x, &y);
switch (dir){
case UP:
y--;
break;
case DOWN:
y++;
break;
case LEFT:
x--;
break;
case RIGHT:
x++;
break;
}
snake[0] = ((x ^ 0) << 4) ^ y;
if (snake[0] == food) {
grow = 1;
food = generate_food();
}
for (i = 0; i<len; i++) {
if (i == 0)
continue;
current = snake[i];
snake[i] = last;
last = current;
}
if (grow) {
snake[len] = last;
len++;
}
for (i = 0; i < 17; i++)
for (j = 0; j < 17; j++)
if (i == 0 || i == 16 || j == 0 || j == 16)
map[i][j] = BAR;
else if (i == fy&&j == fx)
map[i][j] = FOOD;
else
map[i][j] = 0;
for (i = 0; i < len; i++) {
tran(snake[i], &x, &y);
if (snake[i] > 0)
map[y][x] = 1;
}
}
其中有个生产食物的函数,generate_food(),它利用随机数生成函数生成食物坐标,代码如下:
unsigned char generate_food(void)
{
unsigned char food_,fx,fy;
int in_snake=0,i;
srand((unsigned int)time(NULL));
do {
food_ = rand() % 255;
tran(food_, &fx, &fy);
for (i = 0; i < len; i++)
if (food_ == snake[i])
in_snake = 1;
} while (fx == 0 || fx == 16 || fy == 0 || fy == 16 || in_snake);
return food_;
}
随机数生成函数,一般由srand()和rand()函数组成,前者以当前时间为参数提供种子供rand()函数生成更为随机的数。这里用do while语句做了一个筛选,最后产生在边界内且不再蛇身上的食物。
最好剩下一个判断蛇死活的函数,直接上代码吧:
int isalive(void){
int self_eat = 0, i;
unsigned char x, y;
tran(snake[0], &x, &y);
for (i = 1; i < len; i++)
if (snake[0] == snake[i])
self_eat = 1;
return (x == 0 || x == 16 || y == 0 || y >= 16 || self_eat) ? 0 : 1;
}
好了,有了这些函数,把他们组装起来就成了我们的简易贪吃蛇游戏。游戏画面如下: