C/C++实现洛谷P5731 【深基5.习6】蛇形方阵 题目(题解)

 这道题刚开始本来想直接打表过的,整一手面向结果编程哈哈哈,不过仔细一想这样就失去了刷题的意义,我就从头开始自己一步一步想着写出了通用的写法,可能不是最优解(起码是AC代码),但是我感觉要比题解里的都要更好理解些~

基本思路:

1.写出每一个方向的走向判断,判断大致可以分为两部分:

        (1)最外围一圈的判断

        (2)其余内圈的判断

2.定义一个变量用来控制行径方向,避免一直在一个方向判断里打转

3.每次循环开始时,在判断前往数组中填入数字,然后进行走下一步的行动

 详细代码(拿Dev C++写的,可能有些格式不太标准):

#include<iostream>
#include<string.h>
#define RIGHT 1
#define DOWN 2
#define LEFT 3
#define UP 4

using namespace std;

int main(){
	int n;
	cin>>n;
	//用于填入数组(从1到n*n ) 
	int cnt=1;
	//控制二维数组的坐标移动 
	int i=0;
	int j=0;
	//数组 
	int arr[n][n];//用devc++写的代码,支持这种方式创建数组 
	//全部置0,因为是从1开始的,不用担心重复问题,而且还可以用0表示当前位置空 
	memset(arr,0,sizeof(arr));
	//用于标记下一步要往哪个方向走 
	int flag = RIGHT;
	//由题可知方向转变是固定的“右→下→左→上” 
	while(1){
		//当前点放入数据 
		arr[i][j]=cnt++;
		//循环结束条件 
		if(cnt>n*n)break;
		//向右走判断 
		if(RIGHT == flag){
			if(j<n-1) {//如果不是最外围一侧 
				if(arr[i][j+1]==0){//如果当前方向的下一个位置是空的(可以放) 
					//当前位方向 前进一步 
					j++;
				}else{//如果当前方向的下一个位置不是空的(已经放过数字了) 
					//换下一个方向 
					i++;
					flag = DOWN;
				}
				continue;//这一步走完了,后面的省略 
			}else if(j==n-1&&arr[i][j]!=0){//如果是最外围一侧 
                //(arr[i][j]应该不会是空,不过保险起见我还是加了个判断) 
				//换方向 
				i++;
				flag = DOWN;
				continue;
			}
		}
		//向下走判断
		if(DOWN == flag){
			if(i<n-1) {
				if(arr[i+1][j]==0){ 
					i++;
				}else if(arr[i+1][j]!=0){
					j--;
					flag = LEFT;
				}
				continue;
			}else if(i==n-1&&arr[i][j]!=0){
				j--;
				flag = LEFT;
				continue;
			}
		}
		//向左走判断
		if(LEFT == flag){
			if(j>0){
			if(arr[i][j-1]==0){
				j--;
			}else{
				i--;
				flag = UP;
			}
			continue;
			} else if(j==0&&arr[i][j]!=0){
				i--;
				flag = UP;
				continue;
			}
		}
		//向上走判断
		if(UP == flag){
			if(i>0){
			if(arr[i-1][j]==0){
				i--;
				}else{
					j++;
					flag = RIGHT;
				}
				continue;
			}
		}
	}//end of while(1)
	//输出 
	for(int i =0;i<n;i++){
		for(int j =0;j<n;j++){
			printf("%3d",arr[i][j]);
		}
		printf("\n");
	}
	
	return 0;
}

 运行示例:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值