2012-04-09 3 views
-1

프로그램이 전체 미로를 생성하도록 경계 확인을 어디에 두어야합니까? 코드는 셀 사이의 벽을 끊음으로써 그려진 미로가있는 격자를 인쇄해야합니다. 그러나, 당황스럽게도 그리드는 인덱스 0 또는 24에 도달하면 멈 춥니 다. 중지되기 전에 모든 셀을 방문하는 프로그램이 필요합니다 (테두리로 이동하면 되돌아갑니다). 소스 코드 여기OutOfBoundsException입니다. 바운드 체크를 할 곳은 어디입니까?

Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: -1 
     at Grid.genRand(Grid.java:73) 
     at Grid.main(Grid.java:35) 

을 그리고있다 : 나는 매우 빠르게 코드를 간과

import java.awt.*; 
import java.awt.Color; 
import java.awt.Component; 
import java.awt.Graphics; 
import java.util.ArrayList; 

public class Grid extends Canvas { 

    Cell[][] maze; 
    int size; 
    int pathSize; 
    double width, height; 
    ArrayList<int[]> coordinates = new ArrayList<int[]>(); 

    public Grid(int size, int h, int w) { 
     this.size = size; 
     maze = new Cell[size][size]; 
     for(int i = 0; i<size; i++){ 
      for(int a =0; a<size; a++){ 
      maze[i][a] = new Cell(); 
      } 
     } 
     setPreferredSize(new Dimension(h, w)); 
    } 

    public static void main(String[] args) { 
     Frame y = new Frame(); 
     y.setLayout(new BorderLayout()); 
     Panel r = new Panel(); 
     r.setLayout(new BorderLayout()); 
     Grid f = new Grid(25, 400, 400); 
     r.add(f, BorderLayout.CENTER); 
     y.add(r, BorderLayout.CENTER); 
     f.genRand(); 
     f.repaint(); 
     y.pack(); 
     y.setPreferredSize(new Dimension(450, 450)); 
     y.setVisible(true); 
    } 

    public void push(int[] xy){ 
     coordinates.add(xy); 
     int i = coordinates.size(); 
     coordinates.ensureCapacity(i++); 
    } 

    public int[] pop(){ 
     int[] x = coordinates.get((coordinates.size())-1); 
     coordinates.remove((coordinates.size())-1); 
     return x; 
    } 

    public int[] top(){ 
     return coordinates.get((coordinates.size())-1); 
    } 

    public void genRand(){ 
     // create a CellStack (LIFO) to hold a list of cell locations [x] 
     // set TotalCells = number of cells in grid 
     int TotalCells = size*size; 
     // choose a cell at random and call it CurrentCell 
     int m = randomInt(size); 
     int n = randomInt(size); 
     while(m<1){ 
      m = randomInt(size); 
     } 
     while(n<1){ 
      n = randomInt(size); 
      } 
     Cell curCel = maze[m][n]; 
     // set VisitedCells = 1 
     int visCel = 1; 
     int o = 0; 
     int p = 0; 
     int h; 
     int d; 
     int[] q; 
     // while VisitedCells < TotalCells 
     while(visCel < TotalCells){ 
      d = 0; 
      // find all neighbors of CurrentCell with all walls intact 
      if(m!=0&&n!=0){ 
       if(m<size&&n<size){ 
        if(maze[m-1][n].countWalls() == 4) 
         {d++;} 
        if(maze[m+1][n].countWalls() == 4) 
         {d++;} 
        if(maze[m][n-1].countWalls() == 4) 
         {d++;} 
        if(maze[m][n+1].countWalls() == 4) 
         {d++;} 
       } 
      } 
      // if one or more found 
      if(d!=0){ 
       Point[] ls = new Point[4]; 
       ls[0] = new Point(m-1,n); 
       ls[1] = new Point(m+1,n); 
       ls[2] = new Point(m,n-1); 
       ls[3] = new Point(m,n+1); 
       // knock down the wall between it and CurrentCell 
       h = randomInt(3); 
       switch(h){ 
        case 0: o = (int)(ls[0].getX()); 
          p = (int)(ls[0].getY()); 
          curCel.destroyWall(2); 
          maze[o][p].destroyWall(1); 
         break; 
        case 1: o = (int)(ls[1].getX()); 
          p = (int)(ls[1].getY()); 
          curCel.destroyWall(1); 
          maze[o][p].destroyWall(2); 
         break; 
        case 2: o = (int)(ls[2].getX()); 
          p = (int)(ls[2].getY()); 
          curCel.destroyWall(3); 
          maze[o][p].destroyWall(0); 
         break; 
        case 3: o = (int)(ls[3].getX()); 
          p = (int)(ls[3].getY()); 
          curCel.destroyWall(0); 
          maze[o][p].destroyWall(3); 
         break; 
       } 
       // push CurrentCell location on the CellStack 
       push(new int[] {m,n}); 
       // make the new cell CurrentCell 
       m = o; 
       n = p; 
       curCel = maze[m][n]; 
       // add 1 to VisitedCells 
       visCel++; 
      } 
      // else 
      else{ 
       // pop the most recent cell entry off the CellStack 
       q = pop(); 
       m = q[0]; 
       n = q[1]; 
       curCel = maze[m][n]; 
       // make it CurrentCell 
       // endIf 
      } 
     // endWhile 
     } 
    } 

    public int randomInt(int s) { return (int)(s* Math.random());} 

    public void paint(Graphics g) { 
     int k, j; 
     width = getSize().width; 
     height = getSize().height; 
     double htOfRow = height/(size); 
     double wdOfRow = width/(size); 
//checks verticals - destroys east border of cell 
     for (k = 0; k < size; k++) { 
      for (j = 0; j < size; j++) { 
       if(maze[k][j].checkWall(2)){ 
       g.drawLine((int) (k * wdOfRow), (int) (j * htOfRow), (int) (k * wdOfRow), (int) ((j+1) * htOfRow)); 
      }} 
     } 
//checks horizontal - destroys north border of cell 
     for (k = 0; k < size; k++) { 
      for (j = 0; j < size; j++) { 
       if(maze[k][j].checkWall(3)){ 
       g.drawLine((int) (k * wdOfRow), (int) (j * htOfRow), (int) ((k+1) * wdOfRow), (int) (j * htOfRow)); 
      }} 
     } 
    } 
} 

class Cell { 

    private final static int NORTH = 0; 
    private final static int EAST = 1; 
    private final static int WEST = 2; 
    private final static int SOUTH = 3; 
    private final static int NO = 4; 
    private final static int START = 1; 
    private final static int END = 2; 
    boolean[] wall = new boolean[4]; 
    boolean[] border = new boolean[4]; 
    boolean[] backtrack = new boolean[4]; 
    boolean[] solution = new boolean[4]; 
    private boolean isVisited = false; 
    private int Key = 0; 

    public Cell(){ 
    for(int i=0;i<4;i++){wall[i] = true;} 
    } 
    public int countWalls(){ 
    int i, k =0; 
    for(i=0; i<4; i++) { 
    if (wall[i] == true) 
    {k++;} 
    } 
    return k;} 
    public boolean checkWall(int x){ 
    switch(x){ 
     case 0: return wall[0]; 
     case 1: return wall[1]; 
     case 2: return wall[2]; 
     case 3: return wall[3]; 
    } 
    return true; 
    } 
    public void destroyWall(int x){ 
    switch(x){ 
     case 0: wall[0] = false; break; 
     case 1: wall[1] = false; break; 
     case 2: wall[2] = false; break; 
     case 3: wall[3] = false; break; 
     } 
    } 
    public void setStart(int i){Key = i;} 
    public int getKey(){return Key;} 
    public boolean checkVisit(){return isVisited;} 
    public void visitCell(){isVisited = true;} 
} 
+0

미안하지만 수정이 필요합니다. 내 코드를 고치려고했으나 끝까지 다가 갔을 때 벗어났다가 멈추었 기 때문에 여전히 만족스럽지 않습니다. –

+0

나는 또한 try-catch 문을 생각했다 ... try {}에 전체를 넣어야합니까? –

+1

인덱스 -1 또는 인덱스 25가 있는지를 확인하는 코드가 필요하며 물론 그러한 배열 요소가 없기 때문에 예외가 발생합니다. 바운드를 벗어나거나 프로그램 논리를 수정할 수있는 경우에 대비하여 간단히 check 문을 추가 할 수 있습니다. – mbaydar

답변

0

:

  1. 여기

    내가지고있어 이전 오류입니다 좌표가 비어있을 때 top() 또는 pop()을 호출하는 동안 예외가 발생할 수 있습니다. -> 좌표 .get (coordinates.size() - 1) size가 0이면 인덱스 -1 -> BAM을 찾습니다.

  2. 일부 메소드는 매우 복잡해 보입니다. 당신은 이제까지 GUI 물건 (무엇에, 클릭, 보여주는 숨어 콘텐츠를 변경을하지 마십시오 다른

  3. 행동 때문에

  4. 당신은 AWT와 SWING 구성 요소를 함께 사용하지 않는 별도의 방법/기능에 그 functionallity을 분할 해 JFrame, JPanel 등)에서 데드락 (deadlock)이 발생할 수 있습니다.

관련 문제