簡體   English   中英

java中的遞歸迷宮

[英]Recursion maze in java

這個程序不工作,但同時它沒有錯誤提示......每次我輸入起點時,都會顯示起點,但沒有到達終點的路徑,也沒有它通過的路徑。 程序有一個7*11的迷宮,“B”代表障礙物和一個固定的終點,代表“X”,程序要做的是,你可以在里面輸入一個坐標作為你的起點。 然后程序會找到一條從起點到終點的路(路徑也將顯示為“O”)。 在這個過程中我嘗試使用遞歸,但是它不起作用,我不知道為什么。 請幫幫我吧伙計們。

import java.io.*;
public class Maze {
private static final Maze[][] String = null;
String[][] Maze=new String[7][11];
int x,y;
public static void main(String[] args) throws IOException{
    String name;
    int k=0,x1,y1;
    Maze M=new Maze();
    System.out.println("Hello there, would you like to provide your name, please?");
    name=M.Name();
    M.Maze=M.Set(M.Maze);
    M.Print(M.Maze);
    while (k==0){
        System.out.println(name+", now please enter coordinate of the starting point");
        System.out.println("The left top point would be (0,0)");
        System.out.println("Now, please enter the x value:");
        M.x=M.Input();
        System.out.println("And then, please enter the y value");
        M.y=M.Input();
        if (M.Maze[M.y][M.x]==" "){
            M.Maze[M.y][M.x]="$";
            k=1;
        }
        else
            System.out.println("Sorry, you cannot put your starting point there, please try again");
    }
    M.Process(M.x,M.y);
    M.Print(M.Maze);
    System.out.println("$ is the Starting Point");
    System.out.println("X is the Ending Point");
    System.out.println("O is the Path");
}
public static String Name() throws IOException{
    String name;
    BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
    name=br.readLine();
    return name;
}
public static int Input()throws IOException{
    int i;
    BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
    i=Integer.parseInt(br.readLine());
    return i;
}
public static String[][] Set(String Maze[][]){
    for(int i=0;i<7;i++){
        for(int j=0;j<11;j++){
            Maze[i][j]=("B");
        }
    }
    Maze[1][1]=Maze[2][1]=Maze[3][1]=Maze[4][1]=Maze[5][1]=Maze[1][2]=Maze[1][3]=Maze[2][3]=Maze[3][3]=Maze[5][3]=Maze[3][4]=Maze[5][4]=Maze[1][5]=Maze[2][5]=Maze[3][5]=Maze[5][5]=Maze[3][6]=Maze[4][6]=Maze[5][6]=Maze[1][7]=Maze[2][7]=Maze[2][7]=Maze[3][7]=Maze[5][7]=" ";
    Maze[6][7]="X";
    Maze[1][8]=Maze[3][8]=Maze[1][9]=Maze[3][9]=Maze[4][9]=Maze[5][9]=" ";
    return Maze;
}
public static boolean Process(int x1, int y1){
    Maze M=new Maze();
    if (Move(M.Maze,x1,y1)){
        if (End(x1,y1))
            return true;
    }
    else{
        M.Maze[y1][x1]="1";
        if (Process(x1-1,y1)){
            M.Maze[y1][x1]="O";
            return true;
        }
        else if(Process(x1+1,y1)){
            M.Maze[y1][x1]="O";
            return true;
        }
        else if (Process(x1,y1-1)){
            M.Maze[y1][x1]="O";
            return true;
        }
        else if (Process(x1,y1+1)){
            M.Maze[y1][x1]="O";
            return true;
        }
    }
    return false;
}
public static boolean Move(String Maze[][],int x1, int y1){
    if (x1<0||y1<0||x1>6||y1>10)
        return false;
    if ((Maze[y1][x1]=="B")||Maze[y1][x1]=="1")
        return false;
    return true;
}
public static boolean End(int x1, int y1){
    if ((y1==7)&&(x1==5))
        return true;
    return false;
}
public static void Print(String Maze[][]){
    for(int i=0;i<7;i++){
        for(int j=0;j<11;j++){
            System.out.print(Maze[i][j]);
            System.out.print(" ");
        }
        System.out.println(" ");
    }
}
}

我不確定,你想用這條線做什么,因為它在任何地方都沒有使用:

private static final Maze[][] String = null;

我在您的代碼中發現了幾個問題:

  1. 每次您的代碼進入Process方法時,都會使用Maze M=new Maze();創建一個新的Maze實例Maze M=new Maze(); . 新實例不知道您在之前的步驟中所做的額外標記(如 1s),因此它將在兩個相鄰字段之間來回切換,直到您收到 StackOverflowError。
  2. 此外,新的Maze實例未使用Maze進行初始化,因為您沒有在其上調用Set 您應該將Set方法的代碼放在Maze的構造函數中,以免發生此類錯誤。
  3. 但是你的程序甚至還沒有走到這一步。 如果您向Process -method 提供開始字段的坐標,它會想:“我可以移動到指定的字段嗎,如果可以,是否結束?”。 “我可以搬到那里去嗎?”的答案顯然是的,因為您確保開始字段是明確的。 “這就是結局嗎?”的答案沒有。 Process返回 true 並停止。

    --> 你應該怎么做:將Process的遞歸調用放在 if 中,而不是 else 中。 你不需要別的。

  4. 為了防止第 1 項中的StackOverflowError發生(現在確實如此),將Maze一個實例傳遞給Process方法。 請記住每次調用Process都執行此操作,並注意它始終是同一個實例。 刪除在Process中生成新Maze實例的行。

  5. 現在你沒有錯誤,但它仍然不起作用。 這是因為您在Move方法中混淆了 x 和 y 最大索引。 你這樣聲明數組: String[][] Maze=new String[7][11]; . 這意味着最大 x-index 為 10,最大 y-index 為 6。在Move您可以這樣檢查邊界: if (x1<0||y1<0||x1>6||y1>10)

  6. End方法也類似。 如果您數出迷宮中的“X”,則它是左側的第 8 個和頂部的第 6 個。 這對應於 6 的 y-index 和 7 的 x-index。你做了(y1==7)&&(x1==5)

現在它起作用了。 1 是程序嘗試的路徑。

我想你已經注意到你不能從像 main-mehtod 這樣的靜態方法調用非靜態方法。 如果您有一個對象的實例,例如代碼中的M ,您可以使用M.<methodName>()對其調用非靜態方法。

我強烈建議您更仔細地研究面向對象的設計,因為您似乎不了解它。

此外,如果您遵守 Java 命名約定,那就太好了——只有類等以大寫字母開頭,其他所有內容都以小寫字母開頭(變量、方法等)。 對於習慣它的人來說,它使閱讀變得更容易,這幾乎是在課堂上或書本上教過的每個人。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM