面试题。打印矩阵····

notepads 2008-12-02 01:57:31
1 2 3 4 5
14 15 16 17 6
13 20 19 18 7
12 11 10 9 8

请问这样一个矩阵怎么打印出来啊
...全文
334 20 打赏 收藏 转发到动态 举报
写回复
用AI写文章
20 条回复
切换为时间正序
请发表友善的回复…
发表回复
赛铁花 2008-12-08
  • 打赏
  • 举报
回复
测试回复
cqu903 2008-12-04
  • 打赏
  • 举报
回复
算法一:

class Quear{
static int inputNumber=6;
static int lastValue=0;
static int[][] quear=new int[inputNumber][inputNumber];


static void waiWei(int i){
int subQuearRow=inputNumber-2*i;//子矩阵行数
int subQuearLine=subQuearRow;//子矩阵列数
int[] temp=new int[subQuearLine*4-4];//要填入二维数组外圈的值
//数组初始化
for(int k=0;k<temp.length;k++){
temp[k]=k+lastValue+1;
}
//开始填数
int row=i,line=i;//分别表示行和列
int pointer=0;//指向一维数组的元素
for(int c=0;c<subQuearLine;c++){
quear[row][line]=temp[c];
line++;
pointer=c;
}
line--;//上次循环中line超过了4,需要恢复到4.
//System.out.println("Debug:pointer="+pointer+" "+temp[pointer]+" "+line);
//转移方向
pointer++;
row++;
//初始化右列
for(int c=0;c<subQuearRow-1;c++){
quear[row][line]=temp[pointer];
row++;
pointer++;
}
//System.out.println("Debug:pointer="+pointer+" "+temp[pointer]+" "+row+" "+line);
//初始化下行
row--;
line--;
for(int c=0;c<subQuearLine-1;c++){
quear[row][line]=temp[pointer];
line--;
pointer++;
}
//System.out.println("Debug:pointer="+pointer+" "+temp[pointer]+" "+row+" "+line);
line++;
row--;
for(int c=0;c<subQuearRow-2;c++){
quear[row][line]=temp[pointer];
row--;
pointer++;
}
pointer--;
//System.out.println("Debug:pointer="+pointer);
lastValue=temp[pointer];
}

public static void main(String[] args){
int quearNumber=inputNumber/2;//矩阵个数
if(inputNumber%2==1)
quear[quearNumber][quearNumber]=inputNumber*inputNumber;
for(int i=0;i<quearNumber;i++){
waiWei(i);
}
//display.....
for(int c=0;c<inputNumber;c++){
for(int k=0;k<inputNumber;k++){
System.out.print(quear[c][k]+" ");
}
System.out.println();
}
}
}

算法二:

class Quear1{
static int inputNumber=5;
static boolean first=true;
static int defaultNumber=1;
static int[][] quear=new int[inputNumber][inputNumber];
static int lastWay=1;
public static void dosth(){
int row=0,line=0;
for(int c=0;c<inputNumber*inputNumber;c++){
quear[row][line]=defaultNumber;
lastWay=ways(row,line);
switch(lastWay){
case 1:line++;break;
case 2:row++;break;
case 3:line--;break;
case 4:row--;break;
default : System.out.println("error");
}
defaultNumber++;
}
}
//判断方向的方法返回1,2,3,4分别代表右,下,左,上。
static int ways(int row,int line){
int result=lastWay;
switch(lastWay){
case 1:
{if((line==inputNumber-1)||(quear[row][line+1]!=0))
result=2;
break;}
case 2:
{if((row==inputNumber-1)||(quear[row+1][line]!=0))
result=3;
break;}
case 3:
{if((line==0)||(quear[row][line-1]!=0))
result=4;
break;}
case 4:
{if(quear[row-1][line]!=0)
result=1;
break;}
}
return result;
}
public static void main(String[] args){
dosth();
//display.....
for(int c=0;c<inputNumber;c++){
for(int k=0;k<inputNumber;k++){
System.out.print(quear[c][k]+" ");
}
System.out.println();
}
}
}

相比起来,感觉第二个要紧凑点,逻辑也清晰些.大家还有什么高见的请多多指教!
paohui02 2008-12-04
  • 打赏
  • 举报
回复
俺也来一个
paohui02 2008-12-04
  • 打赏
  • 举报
回复
public class PrintRectangle{
int[][] rectangle;
int r,d; //r行,d列
int flag =0; //标记0东,1南,2西,3北.用来表示移动的方向

public PrintRectangle(int r,int d){//
this.r=r;
this.d=d;
rectangle = new int[r][d];
for(int i=0;i<r;i++)
for(int j=0;j<d;j++)
rectangle[i][j]=-1;//初始话数组,全部赋值为-1表示未经过的。
}
private void iniArray(){
int []i={0,0};//初始位置.
int m=1;
rectangle[i[0]][i[1]]=m++;//给第一个位置赋值
int max=r*d;
while(m<=max){ //火车开动了.hoho
next(i);
try{
if(rectangle[i[0]][i[1]]==-1){
rectangle[i[0]][i[1]]=m++;
}
else{
repair(i);
flag=(flag+1)%4;
}
}catch(ArrayIndexOutOfBoundsException e){
repair(i);
flag=(flag+1)%4;
}

}
}
private void next(int []a){//移动一位
switch(flag){
case 0: a[1]++; break;
case 1: a[0]++; break;
case 2: a[1]--; break;
case 3: a[0]--; break;
}
}
private void repair(int []a){//如果移到边界,或者移到已经经过的格子,自动返回一格
switch(flag){
case 0: a[1]--; break;
case 1: a[0]--; break;
case 2: a[1]++; break;
case 3: a[0]++; break;
}
}
public void print(){
iniArray();
for(int i=0;i<r;i++){
for(int j=0;j<d;j++){
System.out.printf("%5d",rectangle[i][j]);

}
System.out.println();
}
}
public static void main(String []args){

PrintRectangle r = new PrintRectangle(Integer.parseInt(args[0]),Integer.parseInt(args[1]));
r.print();

}


}
赛铁花 2008-12-02
  • 打赏
  • 举报
回复
简单测了一下
可以实现非素数的所有正整数的打印,当然是int型整数范围了
请大家测试,有bug给我留言
赛铁花 2008-12-02
  • 打赏
  • 举报
回复

/**
*
* @author hp9016
* @version 1.0
* 功能说明:实现楼主的打印要求
*
*/
public class ForLouZhu {

/**
* 主函数
*/
public static void main(String[] a){

/*
* n为总元素个数
* 可以修改n的值,看看运行效果
*/
int n = 24;
new Array(n).print();
}
}

/**
*
* @author hp9016
* @version 1.0
* 功能说明:存储行数和列数
*
*/
class Row {

/*
* 行数
*/
private static int row;

/*
* 列数,即每行多少个元素
*/
private static int length;

public static int getLength() {
return length;
}
public static void setLength(int length) {
Row.length = length;
}
public static int getRow() {
return row;
}
public static void setRow(int row) {
Row.row = row;
}
}

/**
*
* @author hp9016
* @version 1.0
* 功能说明:实现楼主要求
*
*/
class Array {

/*
* 一共有多少个元素,即二维数组的总元素数
*/
private int n = 0;

/*
* 行数
*/
private int row = 0;

/*
* 列数,即每行多少个元素
*/
private int length = 0;

/*
* 欲打印的数组
*/
private int[][] arr;

/**
* 构造方法
* @param n 总元素个数
*/
public Array(int n){
this.n = n;
}

/**
* 打印数组
*
*/
public void print(){

/*
* 填充数组
*/
setArray();
for(int i = 0; i< row; i++){
for(int j = 0; j < length; j++){
System.out.print(arr[i][j] + " ");
}
System.out.println();
}
}

/**
* 由总元素的数目n来决定数组的行数和列数,
* n的最中间约数作为行数的行数和列数,比如:20
* 则行数为4,列数为5;再比如24,
* 则行数为4,列数为6,再比如25,
* 则行数和列数均为5
*
*/
private void setRow(){
int temp = (n + 1)/2;
int length = n;

for(int i = 1; i <= temp; i++){

if(i >= length){

/*
* 存储到bean中
*/
Row.setLength(length);
Row.setRow(n / length);
break;
}

if(n % i == 0){
length = n / i;
}
}
}

/**
* 核心函数
* 按楼主要求--绕圈填充数组
*
*/
private void setArray(){

/*
* 临时行号
*/
int tempRow = 0;

/*
* 临时列号
*/
int tempLength = 0;

/*
* 当前最小没有被填充的行号
*/
int minRow = 0;

/*
* 当前最小没有被填充的列号
*/
int minLength = 0;

/*
* 当前最大没有被填充的行号
*/
int maxRow = row;

/*
* 当前最大没有被填充的列号
*/
int maxLength = length;

/*
* 记录总元素数目
*/
int i =1;

setRow();
row = Row.getRow();
length = Row.getLength();
arr = new int[row][length];
arr[0][0] = 1;
maxRow = row - 1;
maxLength = length - 1;

/*
* 本while的注释中的"最小"指:没有被填充的最小元素的下标
* "最大"指:没有被填充的最大元素的下标
* 填充的顺序如下:1>2>3>4
* |--1--|
* 4 2
* |--3--|
*
*/
while(i < n){

/*
* 行号最小,列号最小时,类似于上图的1:
* 从左向右这个方向填充数组
*/
if(tempRow == minRow && tempLength == minLength ){

/*
* 设置最大列数
*/
while(arr[tempRow][maxLength] != 0 &&
maxLength > 0){
maxLength--;
}

/*
* 从左向右这个方向填充数组
*/
while(tempLength < maxLength){
tempLength++;
i++;
arr[tempRow][tempLength] = i;
}
}

/*
* 行号最小,列号最大时,类似于上图的2:
* 从上向下这个方向填充数组
*/
if(tempRow == minRow && tempLength == maxLength ){

/*
* 设置最大行数
*/
while(arr[maxRow][tempLength] != 0 &&
maxRow > 0){
maxRow--;
}

/*
* 从上向下这个方向填充数组
*/
while(tempRow < maxRow){
tempRow++;
i++;
arr[tempRow][tempLength] = i;
}
}

/*
* 行号最大,列号最大时,类似于上图的3:
* 从右向左这个方向填充数组
*/
if(tempRow == maxRow && tempLength == maxLength ){

/*
* 设置最小列数
*/
while(arr[tempRow][minLength] != 0 &&
minLength < length - 1){
minLength++;
}

/*
* 从右向左这个方向填充数组
*/
while(tempLength > minLength){
tempLength--;
i++;
arr[tempRow][tempLength] = i;
}
}

/*
* 行号最大,列号最大时,类似于上图的4:
* 从下向上这个方向填充数组
*/
if(tempRow == maxRow && tempLength == minLength ){

/*
* 设置最小行数
*/
while(arr[minRow][tempLength] != 0 &&
minRow < row -1){
minRow++;
}

/*
* 从下向上这个方向填充数组
*/
while(tempRow > minRow){
tempRow--;
i++;
arr[tempRow][tempLength] = i;
}
}
}
}
}
赛铁花 2008-12-02
  • 打赏
  • 举报
回复


/**
*
* @author hp9016
* @version 1.0
* 功能说明:实现楼主的输出要求
*
*/
public class ForLouZhu {

/**
* 主函数
*/
public static void main(String[] a){

/*
* n为总元素个数
* 可以修改n的值,看看运行效果
*/
int n = 24;
new Array(n).print();
}
}

/**
*
* @author hp9016
* @version 1.0
* 功能说明:存储行数和列数
*
*/
class Row {

/*
* 行数
*/
private static int row;

/*
* 列数,即每行多少个元素
*/
private static int length;

public static int getLength() {
return length;
}
public static void setLength(int length) {
Row.length = length;
}
public static int getRow() {
return row;
}
public static void setRow(int row) {
Row.row = row;
}
}

/**
*
* @author hp9016
* @version 1.0
* 功能说明:实现楼主要求
*
*/
class Array {

/*
* 一共有多少个元素,即二维数组的总元素数
*/
private int n = 0;

/*
* 行数
*/
private int row = 0;

/*
* 列数,即每行多少个元素
*/
private int length = 0;

/*
* 欲打印的数组
*/
private int[][] arr;

/**
* 构造方法
* @param n 总元素个数
*/
public Array(int n){
this.n = n;
}

/**
* 打印数组
*
*/
public void print(){

/*
* 填充数组
*/
setArray();
for(int i = 0; i< row; i++){
for(int j = 0; j < length; j++){
System.out.print(arr[i][j] + " ");
}
System.out.println();
}
}

/**
* 由总元素的数目n来决定数组的行数和列数,
* n的最中间约数作为行数的行数和列数,比如:20
* 则行数为4,列数为5;再比如24,
* 则行数为4,列数为6,再比如25,
* 则行数和列数均为5
*
*/
private void setRow(){
int temp = (n + 1)/2;
int length = n;

for(int i = 1; i <= temp; i++){

if(i >= length){

/*
* 存储到bean中
*/
Row.setLength(length);
Row.setRow(n / length);
break;
}

if(n % i == 0){
length = n / i;
}
}
}

/**
* 核心函数
* 按楼主要求--绕圈填充数组
*
*/
private void setArray(){

/*
* 临时行号
*/
int tempRow = 0;

/*
* 临时列号
*/
int tempLength = 0;

/*
* 当前最小没有被填充的行号
*/
int minRow = 0;

/*
* 当前最小没有被填充的列号
*/
int minLength = 0;

/*
* 当前最大没有被填充的行号
*/
int maxRow = row;

/*
* 当前最大没有被填充的列号
*/
int maxLength = length;

/*
* 记录总元素数目
*/
int i =1;

setRow();
row = Row.getRow();
length = Row.getLength();
arr = new int[row][length];
arr[0][0] = 1;
maxRow = row - 1;
maxLength = length - 1;

/*
* 本while的注释中的"最小"指:没有被填充的最小元素的下标
* "最大"指:没有被填充的最大元素的下标
* 填充的顺序如下:1>2>3>4
* |--1--|
* 4 2
* |--3--|
*
*/
while(i < n){

/*
* 行号最小,列号最小时,类似于上图的1:
* 从左向右这个方向填充数组
*/
if(tempRow == minRow && tempLength == minLength ){

/*
* 设置最大列数
*/
while(arr[tempRow][maxLength] != 0 &&
maxLength > 0){
maxLength--;
}

/*
* 从左向右这个方向填充数组
*/
while(tempLength < maxLength){
tempLength++;
i++;
arr[tempRow][tempLength] = i;
}
}

/*
* 行号最小,列号最大时,类似于上图的2:
* 从上向下这个方向填充数组
*/
if(tempRow == minRow && tempLength == maxLength ){

/*
* 设置最大行数
*/
while(arr[maxRow][tempLength] != 0 &&
maxRow > 0){
maxRow--;
}

/*
* 从上向下这个方向填充数组
*/
while(tempRow < maxRow){
tempRow++;
i++;
arr[tempRow][tempLength] = i;
}
}

/*
* 行号最大,列号最大时,类似于上图的3:
* 从右向左这个方向填充数组
*/
if(tempRow == maxRow && tempLength == maxLength ){

/*
* 设置最小列数
*/
while(arr[tempRow][minLength] != 0 &&
minLength < length - 1){
minLength++;
}

/*
* 从右向左这个方向填充数组
*/
while(tempLength > minLength){
tempLength--;
i++;
arr[tempRow][tempLength] = i;
}
}

/*
* 行号最大,列号最大时,类似于上图的4:
* 从下向上这个方向填充数组
*/
if(tempRow == maxRow && tempLength == minLength ){

/*
* 设置最小行数
*/
while(arr[minRow][tempLength] != 0 &&
minRow < row -1){
minRow++;
}

/*
* 从下向上这个方向填充数组
*/
while(tempRow > minRow){
tempRow--;
i++;
arr[tempRow][tempLength] = i;
}
}
}
}
}
zhuyang7654321 2008-12-02
  • 打赏
  • 举报
回复
前面有人问过 “回形打印”

怎么引用留言啊 呵呵
chandlersong 2008-12-02
  • 打赏
  • 举报
回复
你把第一个类实例化时候的参数变成4,5,就是你要的结果了。我这样写发是只要是正方形,就可以回型打印出来。
notepads 2008-12-02
  • 打赏
  • 举报
回复
1 2 3 4 5
16 17 18 19 6
15 24 25 20 7
14 23 22 21 8
13 12 11 10 9

这是运行结果。多了一行。。呵呵
chandlersong 2008-12-02
  • 打赏
  • 举报
回复
第二个类忘记放格子里了

import java.util.Arrays;

/*这是实现类,构造方法的参数为一个row和一个coloum,形成一个矩阵*/
public class Cube {

int[] cube; //用于存放数据
int row; //行数
int coloum; //列数

public Cube(int row,int coloum){ //构造函数
/*初始化*/
this.cube = new int[row*coloum];
Arrays.fill(this.cube,0);
this.row = row;
this.coloum = coloum;
this.initialarry();
}

//形成队列
private void initialarry() {
int step = 1; //下一步要走的值
int id =0; //id号
int next; //存forward函数;
for(int i=1;i<=cube.length;i++){
cube[id] = i;
next = this.forward(id+1);
if(next!=0){ //如果不等于0
step=next;
}
id+=step; //确定下一步要要往哪里走
}
}


@Override
public String toString() {
String output=""; //输出
for(int i = 0;i<this.cube.length;i++){
output+=" "+String.valueOf(cube[i]);
if((i+1)%this.coloum==0){
output+="\n";
}
}
return output;
}

private int forward(int id){ //用于判断一个格子附近的4个格子是否为空
int count=0; //计数器
boolean[] forward = new boolean[4]; //表示方向
Arrays.fill(forward,false); //初始化

/*判断上面的格子*/
if((id-this.coloum)>0 //不是最上面一行
&&cube[id-this.coloum-1]==0){ //还没有赋值
count++;
forward[0] = true; //0表示向上
}

/*判断左面的格子*/
if((id-1)>0 //序列号正常
&&((id-1)%this.coloum)!=0 //不是最左面一列
&&cube[id-2]==0){
count++;
forward[1] = true; //1表示向左
}

/*判断右的格子*/
if((id+1)<=this.cube.length //序列号正常
&&(id%this.coloum)!=0 //不是最右面一列
&&cube[id]==0){
count++;
forward[2] = true; //2表示向右
}

/*判断下面的格子*/
if((id+this.coloum)<=this.cube.length //序列号正常
&&cube[id+this.coloum-1]==0){
count++;
forward[3] = true; //1表示向左
}

/*决定返回值*/
if(count!=1){ //根据观察,如果朋友不为一个的话,是不会转向的。
return 0;
/*如果为一时,那里那里为空,网哪里走*/
}else if(forward[0]){ //上面为空,往上走
return -this.coloum;
}else if(forward[1]){ //左面为空,往左走
return -1;
}else if (forward[2]){ //右面为空,往右走
return 1;
}else if(forward[3]){ //下面为空,往下走
return this.coloum;
}
return 0;
}

}

chandlersong 2008-12-02
  • 打赏
  • 举报
回复

/*1 2 3 4 5
14 15 16 17 6
13 20 19 18 7
12 11 10 9 8

打印如上矩阵*/
public class MainApp {

/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
Cube text = new Cube(5,5);
System.out.print(text);
}

}


import java.util.Arrays;

/*这是实现类,构造方法的参数为一个row和一个coloum,形成一个矩阵*/
public class Cube {

int[] cube; //用于存放数据
int row; //行数
int coloum; //列数

public Cube(int row,int coloum){ //构造函数
/*初始化*/
this.cube = new int[row*coloum];
Arrays.fill(this.cube,0);
this.row = row;
this.coloum = coloum;
this.initialarry();
}

//形成队列
private void initialarry() {
int step = 1; //下一步要走的值
int id =0; //id号
int next; //存forward函数;
for(int i=1;i<=cube.length;i++){
cube[id] = i;
next = this.forward(id+1);
if(next!=0){ //如果不等于0
step=next;
}
id+=step; //确定下一步要要往哪里走
}
}


@Override
public String toString() {
String output=""; //输出
for(int i = 0;i<this.cube.length;i++){
output+=" "+String.valueOf(cube[i]);
if((i+1)%this.coloum==0){
output+="\n";
}
}
return output;
}

private int forward(int id){ //用于判断一个格子附近的4个格子是否为空
int count=0; //计数器
boolean[] forward = new boolean[4]; //表示方向
Arrays.fill(forward,false); //初始化

/*判断上面的格子*/
if((id-this.coloum)>0 //不是最上面一行
&&cube[id-this.coloum-1]==0){ //还没有赋值
count++;
forward[0] = true; //0表示向上
}

/*判断左面的格子*/
if((id-1)>0 //序列号正常
&&((id-1)%this.coloum)!=0 //不是最左面一列
&&cube[id-2]==0){
count++;
forward[1] = true; //1表示向左
}

/*判断右的格子*/
if((id+1)<=this.cube.length //序列号正常
&&(id%this.coloum)!=0 //不是最右面一列
&&cube[id]==0){
count++;
forward[2] = true; //2表示向右
}

/*判断下面的格子*/
if((id+this.coloum)<=this.cube.length //序列号正常
&&cube[id+this.coloum-1]==0){
count++;
forward[3] = true; //1表示向左
}

/*决定返回值*/
if(count!=1){ //根据观察,如果朋友不为一个的话,是不会转向的。
return 0;
/*如果为一时,那里那里为空,网哪里走*/
}else if(forward[0]){ //上面为空,往上走
return -this.coloum;
}else if(forward[1]){ //左面为空,往左走
return -1;
}else if (forward[2]){ //右面为空,往右走
return 1;
}else if(forward[3]){ //下面为空,往下走
return this.coloum;
}
return 0;
}

}



notepads 2008-12-02
  • 打赏
  • 举报
回复
1 2 3 4 5
14 15 16 17 6
13 20 19 18 7
12 11 10 9 8

是有规律的。。回形的,
发出来可能格式变乱了而已
_______-- 2008-12-02
  • 打赏
  • 举报
回复
有点难度,标记关注
hbgzg3006 2008-12-02
  • 打赏
  • 举报
回复
就是回型打印,貌似前面有人问过
jcyan 2008-12-02
  • 打赏
  • 举报
回复
其实就是一个二维数组啊
guogaocheng 2008-12-02
  • 打赏
  • 举报
回复
有规律,问问楼主初始数组是不是1-20有序的?
guogaocheng 2008-12-02
  • 打赏
  • 举报
回复
这机器没环境,回头研究研究。
jcyan 2008-12-02
  • 打赏
  • 举报
回复
有这么简单的面试题?!
双重循环
lshy168 2008-12-02
  • 打赏
  • 举报
回复
不会吧?这样子都没规律了怎么打啊。

62,615

社区成员

发帖
与我相关
我的任务
社区描述
Java 2 Standard Edition
社区管理员
  • Java SE
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧