算法的乐趣c/c++ —— 1.1.9入门习题

声明:摘选自“   算法竞赛入门经典(第2版)”作者:    刘汝佳    /    陈锋     ISBN:9787302291077

谜题

有一个5 * 5的网格,其中恰好有一个格子是空的,其他格子各有一个字母。一共有4种指令:A,B,L,R,分别表示把空格上,下,左,右的相邻字母移到空格中。输入初始网格和指令序列(以数字0结束),输出指令执行完毕后的网格。如果有非法指令,应输出“这个拼图没有最终的配置。”,例如,图左中执行ARRBBL0后,效果如图右所示。
 

 解题思路

其实只要利用的getchar()循环读入字符,然后将其按照5×5的格式存放在二维字符数组,然后记录空格的位置,再根据就输入的命令将空格与对应的字符交换值即可:

#include<stdio.h>
#include<string.h>
char s[6][6];   //定义一个存储字母的二维字符串数组 
int main()
{
	char c, comd;        //c用于存放读取的字符,comd用于存放读取的命令字符 
	int i=0, j=0, x, y;          //i,j用于记录网格的坐标,x,y用于记录空格的坐标 
	while((c = getchar()) !='0')     //循环读取字符 ,当输入‘0’时停止循环 
	{
		if(c != '0') s[i][j] = c;    //因为停止命令是‘0’,我们必须判断是否将‘0’读入了,如果读入,则不会将其放入数组s[][] 
		if(c == ' ')          //如果读入的是空格,用x,y记录其坐标 
		{
			x = i;
			y =j ;
		} 
		j ++;                //s[i][j]向右移动一位进行记录 
		if(j==5)             //当s[i][j]第一行存储满了之后,向下移动一位 
		{
			i ++;
			j = 0;
		}
	}
	for(int m=0; m<5; m++)          //将读入的字符按照5*5格式打印 
	{
		for(int n=0; n<5; n++)
		{			
			printf("%c ", s[m][n]);
			if(n==4) printf("\n");
		}
	}	
	
	while((comd=getchar()) != '0')   //循环读入命令字符,遇到‘0’停止读取,结束循环 
	{
		if(comd == 'A')   //向上移动空格 
		{
			s[x][y] = s[x-1][y];
			s[x-1][y] = ' ';
			x = x-1;
		}
		else if(comd == 'B')        //向下移动空格 
		{
			s[x][y] = s[x+1][y];
			s[x+1][y] = ' ';
			x = x+1;
		}
		else if(comd == 'R')        //向右移动空格 
		{
			s[x][y] = s[x][y+1];
			s[x][y+1] = ' ';
			y = y+1;
		}
		else if(comd == 'L')         //向左移动空格 
		{
			s[x][y] = s[x][y-1];
			s[x][y-1] = ' ';
			y = y-1;
		}
		else                       //输入非法字符时输出 
		{
			printf("This puzzle has no final configuration.");
			return 0;
		}
	}
	printf("\n");                   //换行,以便分辨原始数组与处理后的数组 
	for(int m=0; m<5; m++)           //将处理后的字符按照5*5格式打印 
	{
		for(int n=0; n<5; n++)
		{			
			printf("%c ", s[m][n]);
			if(n==4) printf("\n");
		}
	}	

} 

效果图如下:

 

猜你喜欢

转载自blog.csdn.net/lpp5406813053/article/details/84864286