用C語言如何實現貪吃蛇程式設計
貪吃蛇遊戲在理論上是可以無限的進行下去的(除了撞牆和咬到自己),那麼遊戲主體就一定是個迴圈。下面是小編為大家帶來的關於用C語言如何實現貪吃蛇程式設計的知識,歡迎閱讀。
貪吃蛇實現原理:貪吃蛇遊戲在理論上是可以無限的進行下去的(除了撞牆和咬到自己),那麼遊戲主體就一定是個迴圈。
蛇是如何動起來的?在這裡就是通過不斷改變蛇的座標,然後根據蛇的座標不斷重新整理螢幕在視覺上形成蛇的移動效果。
食物出現在隨機位置(當然不能出現在障礙物和蛇身上)。
蛇能吃到食物其實就是蛇頭的座標與食物的座標重合時。
當蛇咬到自己或者撞到牆的時候遊戲結束(座標判斷)
#include
#include
#include
#include
#include
//72,80,75,77是方向鍵對應的鍵值
#define UP 72
#define DOWN 80
#define LEFT 75
#define RIGHT 77
#define SNAKE 1 //蛇的座標標識
#define FOOD 2 //食物的座標標識
#define BAR 3 //牆的座標標識
//初始化地圖 17*17
char map[17][17] = {0};
//初始化蛇頭座標
unsigned char snake[50] = {77};
//初始化食物座標
unsigned char food = 68;
//蛇長
char len = 1;
//儲存座標數字與x、y的轉換函式
void tran(unsigned char num,unsigned char * x,unsigned char * y);
//列印遊戲
void print_game(void);
//獲取方向函式(注意當蛇身長度超過一節時不能回頭)
int get_dir(int old_dir);
//移動蛇身函式(遊戲大部分內容在其中)
void move_snake(int dir);
//生產食物的函式
unsigned char generate_food(void);
//判斷蛇死活的函式(判斷了蛇是否撞到邊界或者自食)
int isalive(void);
int main(void){
int dir = UP; //初始方向預設向上,UP是我們定義的巨集
//按道理該遊戲是可以無限繼續下去的,因此是個迴圈
while(1){
print_game(); //列印遊戲
dir = get_dir(dir); //獲取方向(我們摁下的方向)
move_snake(dir); //移動蛇身
if(!isalive()){ //判斷蛇的生命狀態
break;
}
}
printf("Game Over!");
return 0;
}
//
void tran(unsigned char num,unsigned char * x,unsigned char * y){
*x = num >> 4;
*y = (unsigned char)(num << 4) >> 4; //注意這裡要做個強制型別轉換
//根據彙編,如果不做強制轉換,y的值與num的'值相同
}
void print_game(void){
int i,j;
//根據地圖上每點的情況繪製遊戲( i 表示 x 軸,j 表示 y 軸),按行列印,j表示行,i表示列
for(j = 0;j < 17;j ++){
for(i = 0;i < 17;i ++){
//空白地方
if(map[i][j] == 0){
put' ');
}
//蛇身
else if(map[i][j] == SNAKE){
put'*');
}
//圍欄
else if(map[i][j] == BAR){
put'#');
}
//食物
else if(map[i][j] == FOOD){
put'$');
}
}
put'');
}
Sleep(500); //休眠函式 將程序掛起500ms,包含在window.h(在linux下用 sleep(),#include )
system("cls"); //清屏函式 配合下一次 print_game() 起到重新整理作用,包含在stdlib.h中
}
int get_dir(int old_dir){
int new_dir = old_dir;
//用kbhit()與getch()組合實現鍵盤響應
//kbhit() 檢查當前是否有鍵盤輸入,若有則返回一個非0值,否則返回0
//getch() 用ch=_getch();會等待你按下任意鍵之後,把該鍵字元所對應的ASCII碼賦給ch,再執行下面的語句。
if(_kbhit()){
_getch(); //第一次輸出的方向鍵的擴充套件值,第二次是方向鍵的實際值,只有方向鍵上下左右這樣
new_dir = _getch(); //getch()函式要使用兩次,原因是因為第一次返回的值指示該鍵擴充套件的字元,第二次呼叫才返回實際的鍵程式碼
//如果蛇身長度大於1,則不能回頭,如果摁回頭方向,則按原來方向走
//abs(new_dir - old_dir) == 2 表示 |LEFT-RIGHT|
//abs(new_dir - old_dir) == 8 表示 |UP-DOWN|
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; //last與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; //將x,y換回一個數
//x與0抑或保留原值
//將x與y重新合成一個值
//蛇吃到了食物
if (snake[0] == food) {
grow = 1;
food = generate_food(); //產生新食物
}
for (i = 0; i
if (i == 0) //如果只有頭,跳過,因為前面已更新蛇頭座標
continue;
current = snake[i]; //將當前操作的蛇節座標儲存到current裡
snake[i] = last; //完成當前操作蛇節座標的更新
last = current; //last記錄的是上一次操作蛇節的座標,這次操作已經結束,故把current賦給last
}
//如果蛇邊長了
if (grow) {
snake[len] = last;
len++;
}
for (j = 0; j < 17; j ++){ //將邊界與食物加到地圖裡去(i,j 對應 x軸和y軸)
for (i = 0; i < 17; i ++){
if (i == 0 || i == 16 || j == 0 || j == 16){
map[i][j] = BAR;
}
else if (i == fx&&j == fy){
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[x][y] = SNAKE;
}
}
}
}
unsigned char generate_food(void)
{
unsigned char food_,fx,fy;
int in_snake=0,i;
//以當前時間為引數提供種子供rand()函式生成更為隨機的數
srand((unsigned int)time(NULL));
//迴圈產生在邊界內且不在蛇身上的食物
do {
food_ = rand() % 255;//產生一個0--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_;
}
int isalive(void)
{
int self_eat = 0;
int 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;
}
-
2017年3月計算機二級C語言考試摸底測試題
以下是yjbys考試網小編整理的2017年3月計算機二級C語言考試摸底測試題,希望對大家有所幫助,祝大家計算機二級考試順利通過。一、選擇題(每小題1分。)(1)程式流程圖中帶有箭頭的線段表示的是()。A.圖元關係B.資料流C.控制流D.呼叫關係(2)結構化程式設計的基本原則...
-
C語言if else語句彙總
對於很多情況,順序結構的程式碼是遠遠不夠的,大家都接觸過C語言吧,下面是小編為大家整理的C語言ifelse語句,希望對大家有所幫助。C語言ifelse語句在C語言中,使用if和else關鍵字對條件進行判斷。請先看下面的程式碼:#includeintmain(){intage;printf("請輸入你的年齡:");sc...
-
C語言精選面試題詳解
C語言是IT程式設計中最基礎的語言,在面試中,基本可以忽略又或者格外重要。下面是小編為大家整理的C語言精選面試題詳解,歡迎參考~分析這些面試題,本身包含很強的趣味性;而作為一名研發人員,通過對這些面試題的深入剖析則可進一步增強自身的內功。試題1:以下是引用片段:voi...
-
2017年計算機二級考試C語言備考題及答案
計算機二級對於很多考生來說還是比較有難度的,那麼怎樣順利通過二級考試呢?這就需要大家平時多練習和找方法了。以下是本站小編整理的2017年計算機二級考試C語言備考題及答案,希望對大家有幫助!1.(A)是構成C語言程式的基本單位。A、函式B、過程C、子程式D、子例...