貪食蛇涵蓋遊戲循環、鍵盤輸入、雙緩衝渲染、鏈表/陣列數據結構、隨機生成、碰撞檢測等核心遊戲開發概念,且無需圖形庫,僅用 conio.h、windows.h 即可在 Windows 控制台運行。本文提供完整可編譯代碼,並深度解析蛇身轉彎同步、食物生成、分數統計等關鍵邏輯。
#define MAX_TURN 1000
#define INIT_LEN 8
// 全局狀態
char snakeBody[1000] = "@*******"; // '@' 頭,'*' 身體,長度 INIT_LEN
int snakeLen = INIT_LEN;
int head[2], tail[2]; // 頭尾座標
int direction; // 0上 1下 2左 3右
int turnPoints[MAX_TURN][2]; // 轉彎點隊列
int headTurnIdx = 0, tailTurnIdx = 0; // 頭/尾轉彎點索引
int food[2]; // 食物座標
int score = 0;
bool gameOver = false;
設計亮點:用轉彎點隊列而非逐幀移動整條蛇,將移動複雜度從 O(n) 降為 O(1)——頭記錄轉彎點,尾跟隨消費轉彎點。
void main() {
while (!gameOver) {
printIntro(); // 規則界面
waitKey(); // 任意鍵開始
initGame(); // 重置狀態、畫初始蛇、生成食物
controlLoop(); // 輸入處理 + 移動 + 碰撞檢測 核心循環
showResult(); // 顯示分數、詢問重玩
}
}
control()getch() 非阻塞讀取,識別方向鍵(-32 前導 + H/P/K/M)。if (dir==LEFT||RIGHT) 允許 UP/DOWN)。turnPoints[headTurnIdx++] = head。moveUp/Down/Left/Right()gotoxy(newHead); putchar('@');gotoxy(oldHead); putchar('*');gotoxy(tail); putchar(0);(或空格)。updateTail() 推進尾部。updateTailPosition()
// 核心邏輯:尾巴朝向下一個轉彎點移動
if (tailTurnIdx < headTurnIdx) {
int tx = turnPoints[tailTurnIdx][0];
int ty = turnPoints[tailTurnIdx][1];
if (tail[0] < tx) tail[0]++;
else if (tail[0] > tx) tail[0]--;
else if (tail[1] < ty) tail[1]++;
else if (tail[1] > ty) tail[1]--;
// 到達轉彎點
if (tail[0]==tx && tail[1]==ty) tailTurnIdx++;
} else {
// 無轉彎點,直線追趕頭
if (tail[0] < head[0]) tail[0]++;
// ... 其他方向
}
此法完美模擬蛇身「拐彎延遲」效果,無需移動中間節點。
generateFood() / eatFood()tail 回退到 oldTail,snakeBody[snakeLen++] = '*',分數+1。cursor[x] >= RIGHT_EDGE 等判斷,超界不移動(或判負)。bool occupied[H][W] 優化至 O(1))。
#include <stdio.h> #include <windows.h> #include <conio.h> #include <time.h>
#define W 80 #define H 25 // 畫面大小
// ... 宏定義、全局變量同上 ...
void gotoxy(int x,int y){ COORD c={x,y}; SetConsoleCursorPosition(GetStdHandle(STD_OUTPUT_HANDLE),c); }
void initGame() {
snakeLen=INIT_LEN; head[0]=W/2; head[1]=H/2; tail[0]=head[0]-INIT_LEN+1; tail[1]=head[1];
direction=3; headTurnIdx=tailTurnIdx=0; score=0; gameOver=false;
system("cls"); generateFood();
gotoxy(tail[0],tail[1]); for(int i=snakeLen-1;i>=0;--i) putchar(snakeBody[i]);
}
void controlLoop() {
while(!gameOver){
if(_kbhit()){
int ch=_getch();
if(ch==-32){ ch=_getch(); /* 處理方向鍵,更新 direction、記錄轉彎點 */ }
else if(ch==3) gameOver=true; // Ctrl+C 退出
}
move(); // 根據 direction 調用 moveUp/Down/Left/Right
if(head[0]==food[0] && head[1]==food[1]) { eatFood(); generateFood(); }
Sleep(80); // 控制速度
}
}
// ... moveUp/Down/Left/Right, updateTailPosition, generateFood, eatFood 完整實現 ...
int main(){ srand(time(0)); main(); return 0; } // 入口
WriteConsoleOutput 刷新,消除閃爍。ncurses (Linux/macOS) 或自寫 ANSI 轉義序列抽象層。控制台貪食蛇是「小而全」的系統訓練項目:轉彎點隊列巧妙解耦頭尾移動,gotoxy 實現精確光標控制,模塊化結構清晰易擴展。建議讀者以此為基礎,逐步加入雙緩衝、關卡系統、網絡對戰,體驗從「代碼跑通」到「架構優雅」的成長。