C语言的小扫雷

前言:
之前一直想实现下扫雷,偶然在贴吧里看到有人出题,于是心血来潮就写了下。

题目:

扫雷游戏是Windows里一款十分经典的单机小游戏,请你用C程序自己建立一个扫雷小游戏。
系统可以随机产生一个m行n列的雷区,包含若干颗地雷,用户可以挖开一个区域,如果是地雷,游戏结束,失败;
如果不是,显示出它周围的地雷个数,如果能把所有安全的地区找出来,获胜。 注:每个格子周围格有八个:上、下、左、右、左上、右上、左下、右下。
运行结果:
请输入雷区的范围:
3 5
X X X X X
X X X X X
X X X X X
请输入安全的位置:
2 2
X X X X X
X 3 X X X
X X X X X
请输入安全的位置:
3 4
X X X X X
X 3 X X X
X X X O X
很不幸,你踩到雷了,游戏结束!

代码:

#include<stdio.h>
#include <stdlib.h>
#include <time.h>

int dir[4][2] = {{-1,0},{1,0},{0,-1},{0,1}};
int around[8][2] = {{-1,-1},{-1,0},{-1,1},{0,-1},{0,1},{1,-1},{1,0},{1,1}};
int x,y,z; //行 列 雷 
int *map; //雷区
char *view; //玩家视野 

//初始化雷区 
void init()
{
	for(int i=0;i<x*y;i++)
		map[i]=0;
	for(int i=0;i<x*y;i++)
		view[i]='O';
	
	srand((unsigned)time(NULL));
	int n = z>x*y?x*y:z; 
	while(n--)
	{
		int r = rand()%(x*y);
		while(map[r])
			r = rand()%(x*y);
		map[r] =1;
	} 
}

//周围雷数 
int checkMine(int px, int py)
{
	int count = 0;
	for(int i=0;i<8;i++)
	{
		int nx = px+around[i][0];
		int ny = py+around[i][1];
		if(nx>=0&&nx<x&&ny>=0&&ny<y&&map[y*nx+ny]==1)
			count++;
	}
	return count;
}

//排雷 
void clearMine(int px, int py)
{
	int num = checkMine(px,py);
	view[y*px+py]=num==0?'.':'0'+num;
	for(int i=0;num==0&&i<4;i++)
	{
		int nx = px+dir[i][0];
		int ny = py+dir[i][1];
		if(nx>=0&&nx<x&&ny>=0&&ny<y&&map[y*nx+ny]==0&&view[y*nx+ny]=='O')
			clearMine(nx,ny);
	}
}

//检查是否获胜 
int checkWin()
{
	int n=0;
	for(int i=0;i<x*y;i++)
		if(view[i]=='O')
			n++;
	return n==z;
}


//雷区视图
void mapScreen()
{
	printf("\n"); 
	for(int i=0; i<x*y;i++)
	{
		printf("%d ",map[i]);
		if((i+1)%y==0) printf("\n");
	}
}

//玩家视图 
void viewScreen()
{
	for(int i=0; i<x*y;i++)
	{
		printf("%c ",view[i]);
		if((i+1)%y==0) printf("\n");
	}
}

int main()
{
	printf("请输入雷区参数(行 列 地雷数):\n"); 
	scanf("%d %d %d",&x,&y,&z);
	map = (int *) malloc(sizeof(int)*x*y);
	view = (char *) malloc(sizeof(char)*x*y);
	
	init(); //生成雷区
	viewScreen(); //打印玩家视图
	//mapScreen(); //查看雷区(作弊)
	
	int px,py,isWin;
	while(1)
	{
		printf("请输入安全的位置:\n"); 
		scanf("%d %d",&px,&py);
		px--; py--;
		if(px<0||px>=x||py<0||py>=y)
		{
			printf("范围有误!\n");
			continue;
		}
		
		//若踩雷游戏结束 
		if(map[y*px+py]){
			//将所有地雷显示出来
			for(int i=0; i<x*y;i++)
			{
				if(map[i]==1)
					printf("X ");
				else
					printf("%c ",view[i]);
				if((i+1)%y==0) printf("\n");
			}
			isWin = 0;
			break;
		}
		
		//否则对安全座标排雷 
		if(view[y*px+py]=='O')
			clearMine(px,py);
			
		viewScreen(); //打印玩家视图
		
		//判断是否获胜
		if(checkWin()) 
		{
			isWin = 1;
			break;
		}
	}
	
	if(isWin)
		printf("恭喜获胜!");
	else
		printf("很不幸,你踩到雷了,游戏结束!");
		
	return 0;
}

效果图:
在这里插入图片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章