2012-03-13 4 views
2

Я написал фрагмент кода для перемещения объекта в случайном направлении на Java. Есть две функции.Проблема с произвольными номерами в Java

  1. FindRandomDirection - Получает случайное направление из 8 возможных направлений (направления представлены номера 1,2,3,4,6,7,8,9 в цифровой клавиатуре). Выполняется проверка, находится ли объект рядом с любой из границ. Если это так, объект будет двигаться в направлении от границы.

  2. MoveObject - изменяет координаты (X, Y) объекта, перемещаясь по постоянному шагу.

Но какие значения я даю для X, Y; после повторения процесса несколько раз (700 или более) значения X, Y становятся {X: 20-50} и {Y: 450-465}.

I.e.

Case 1: (x:35,y:65) becomes (x:35, y:465) 
Case 2: (x:30, y:455) becomes (x:30, y:460) 
Case 3: (x:435, y:65) becomes (x:25, y:460) 
Case 4: (x:430, y:465) becomes (x:40, y:460) 

Я хотел бы, почему после нескольких итераций х, у точки сходится к этим значениям, даже если я генерировать числа в случайном порядке.

Ниже приведен код для того же.

import java.io.*; 
public class bug 
{ 
    //public static int x = 35; 
    //public static int y = 60; 

    //public static int x = 35; 
    //public static int y = 460; 

    //public static int x = 435; 
    //public static int y = 60; 

    public static int x = 435; 
    public static int y = 460; 

    public static final int NORTH = 8; 
    public static final int EAST = 6; 
    public static final int WEST = 4; 
    public static final int SOUTH = 2; 
    public static final int NORTHEAST = 9; 
    public static final int NORTHWEST = 7; 
    public static final int SOUTHWEST = 1; 
    public static final int SOUTHEAST = 3; 
    public static final int STEP = 5; 

    //Function to move the object in a specified direction. 
    public static void moveObject(int direction) 
    { 
      double nX = 0, nY=0; 
      switch(direction) 
      { 
      case NORTH: 
       nY = y- STEP; 
       nX = x; 
       break; 
      case SOUTH: 
       nY = y+ STEP; 
       nX = x; 
       break; 
      case EAST:    
       nY = y; 
       nX = x + STEP; 
       break; 
      case WEST: 
       nY = y; 
       nX = x- STEP;    
       break; 
      case NORTHEAST: 
       nX = x + STEP; 
       nY = y- STEP; 
       break; 
      case NORTHWEST: 
       nX = x- STEP; 
       nY = y- STEP; 
       break; 
      case SOUTHEAST: 
       nX = x + STEP; 
       nY = y+ STEP; 
       break; 
      case SOUTHWEST: 
       nX = x- STEP; 
       nY = y+ STEP; 
       break; 
      } 
      x = (int) nX; 
      y = (int) nY; 
      System.out.println("Direction: "+direction+"; X: "+x+"; Y: "+y); 
     } 
//Function to move the object in a random direction 
//Also if wall(Border) is present the object should move in proper direction 
    public static int findRandomDirection(int objObjectX, int objObjectY) 
    { 
     int[] move = {1,2,3,4,0,6,7,8,9}; 
     int randDir=0; 
     //Generate a random direction to move. Generate new direction if the objected can not be moved in a direction 
     do 
     { 
      java.util.Random randomGenerator = new java.util.Random(); 
      randDir = randomGenerator.nextInt(8); 

      //If the object lies near East Border, it can not move in that direction 
      if(objObjectX <= 25) 
      { 
       move[0] = 0; 
       move[3] = 0; 
       move[6] = 0; 
      } 

      //If the object lies near West Border, it can not move in that direction 
      if(objObjectX >= 465) 
      { 
       move[2] = 0; 
       move[5] = 0; 
       move[8] = 0;     
      } 

      //If the object lies near North Border, it can not move in that direction 
      if(objObjectY <= 25) 
      { 
       move[6] = 0; 
       move[7] = 0; 
       move[8] = 0; 
      } 

      //If the object lies near South Border, it can not move in that direction 
      if(objObjectY >= 465) 
      { 
       move[0] = 0; 
       move[1] = 0; 
       move[2] = 0;     
      } 
     } while(move[randDir]==0); 
     return move[randDir];  
    } 
    public static void main(String[] args) 
    { 
     for(int i = 0; i<1000;i++) 
     { 
     int dir=findRandomDirection(x,y); 
     moveObject(dir); 
     } 
    } 
} 

Так что со временем мой объект перемещается в левый нижний угол доски. Пожалуйста, помогите мне найти ошибку.

+3

Вы никогда не должны повторно инициализировать генератор псевдослучайных чисел в цикле. Создайте объект один раз для класса и повторно используйте его. В то время как 'java.util.Random' включает код, чтобы справиться с этой ошибкой, все же лучше не брать неприятные привычки. – Joey

ответ

6

Поскольку вы используете nextInt(8), возвращаемое значение всегда будет находиться между 0 и 7 (включительно). Поскольку 8 никогда не возвращается, движение смещается в противоположном направлении. Вероятно, вы захотите использовать nextInt(9), чтобы вернуть значение от 0 до 8 (включительно).

редактировать: Для того, чтобы уточнить, так как «8» никогда не выбран в качестве случайного направления, и moves[8]==9, объект никогда не двигается в NORTHEAST направления, что означает, с течением времени она будет иметь тенденцию путешествовать SOUTHWEST.

Также, как @Joey сказал выше, вы не должны повторно инициализировать объект Random каждый раз, но это не то, что вызывало дрейфующее поведение.

+0

Забавно, как этот вопрос сидит здесь в течение 45 минут без ответа (я знаю, я пытался понять это), тогда вашему ответу удается привлечь еще 2, которые почти одинаковы :) – ggrigery

3

Когда вы выбираете направление, вы выбираете значение от 0 до 7 включительно. Эти значения (в вашем отображении) соответствуют:

public static final int SOUTHWEST = 1; 
public static final int SOUTH = 2; 
public static final int SOUTHEAST = 3; 
public static final int WEST = 4; 
public static final int EAST = 6; 
public static final int NORTHWEST = 7; 
public static final int NORTH = 8; 

Но обратите внимание, что это не будет никогда быть выбраны:

public static final int NORTHEAST = 9; 

Таким образом, это не удивительно для меня, что ваш код, кажется, смещена к юго-востоку ...

1

Метод nextInt(n) возвращает номера с нуля, включительно, до n, эксклюзивный. Поскольку вы передаете значение 8, результаты взяты из набора из 8 значений, 0 – 7. Таким образом, девятый элемент массива, который представляет северо-восточное направление, никогда не выбирается.

Это смещение против северо-востока приводит к возможной миграции на юго-запад.

Смежные вопросы