2011-04-04 19 views
1

我有以下代碼,並且我可以看到值之間有連接。然而,我可以不把我的腦袋集中在一起,並找出如何用一些加減模式刪除開關語句。會真正appriciate一些幫助,讓這種方法更順暢。我有一個腦凍結,幫助我使這種方法高效:>

的標題變量或者是0,1,2或3。

public static int getRotation(Point currentPoint, Point nextPoint, int heading) { 
    int rotation = -1; 
    if(currentPoint.getX() < nextPoint.getX()) /* DRIVE WEST */ { 
     switch(heading) { 
      case 0: rotation = 1; break; 
      case 1: rotation = 0; break; 
      case 2: rotation = 3; break; 
      case 3: rotation = 2; break; 
     } 
    } else if(currentPoint.getX() > nextPoint.getX()) /* DRIVE EAST */ { 
     switch(heading) { 
      case 0: rotation = 3; break; 
      case 1: rotation = 2; break; 
      case 2: rotation = 1; break; 
      case 3: rotation = 0; break; 
     } 
    } else if(currentPoint.getY() < nextPoint.getY()) /* DRIVE NORTH */ { 
     switch(heading) { 
      case 0: rotation = 0; break; 
      case 1: rotation = 3; break; 
      case 2: rotation = 2; break; 
      case 3: rotation = 1; break; 
     } 
    } else if(currentPoint.getY() > nextPoint.getY()) /* DRIVE SOUTH */ { 
     switch(heading) { 
      case 0: rotation = 2; break; 
      case 1: rotation = 1; break; 
      case 2: rotation = 0; break; 
      case 3: rotation = 3; break; 
     } 
    } 

    return rotation; 
} 

編輯:我沒有忘記提及NextPoint公司只能是+ -x或相比當前點年。如果currentPoint是(0,0)newPoint必須是(-1,0),(1,0),(0,-1)或(0,1)。

+2

你確實意識到你的算法更喜歡在南北向之前驅動西部和東部? – orlp 2011-04-04 15:02:18

+0

我甚至不確定這是否正確。在效率之前我會擔心這一點。你如何移動NW或SE? – duffymo 2011-04-04 15:07:41

+1

使用枚舉。這就是他們在那裏。 http://download.oracle.com/javase/tutorial/java/javaOO/enum.html – I82Much 2011-04-04 15:08:21

回答

3

你可以試試。

int eastWest = Double.compare(currentPoint.getX(), nextPoint.getX()) 
if (eastWest == 0) { 
    int northSouth = Double.compare(currentPoint.getX() , nextPoint.getX()) 
    /* DRIVE NORTH (-1), SOUTH (+1) */ 
    if (northSouth == 0) 
     rotation = -1; 
    else 
     rotation = (5 + northSouth - heading) % 4; 
} else { 
    /* DRIVE WEST (-1), EAST (+1) */ 
    rotation = heading^(2 + eastWest); 
} 

注:我希望看到一些symetry這些功能是每個方向上似乎有不同的組合,並且不健全的權利。

+1

Drive South可能是'(6 - heading)%4'。 – kennytm 2011-04-04 15:05:13

+0

@KennyTM,謝謝。 – 2011-04-04 15:06:18

+0

如果你將Drive West寫成'(5 - heading)%4',你會看到'對稱性'。 – kennytm 2011-04-04 15:08:32

3

最好的方法是使用數學矢量來表示你當前的方向。

0

當然你可以優化以上的方法,但將來在維護中這種代碼的和平將非常難以理解。

如果您還沒有更好的主意,請嘗試創建4個將標題映射到旋轉值的地圖。想想創建一些枚舉來顯示什麼是神祕的1 2 3 4.

2

所有的旋轉值是「0321」(北:0321,東:3210,南:2103,西:1032)的旋轉版本。一個簡單的解決方案是創建一個包含「321」的數組,併爲每個案例使用不同的索引訪問它。僞代碼:

initialise array arr with 0,3,2,1,0,3,2,1 
index = 0 for north, 1 for east, 2 for south, 3 for west 
rotation = arr[index+heading]; 

編輯:我認爲,我們可以用這個數學表達式,而不是數組:

index = 0 for north, 1 for east, 2 for south, 3 for west 
rotation = (8 - (index+heading)) % 4; 
2

它幾乎沒有可讀的,但如果你想少寫代碼,你可以得到結果簡單的數學:

public static int getRotation(Point currentPoint, Point nextPoint, int heading) { 
    int dx = (int) Math.signum(nextPoint.getX() - currentPoint.getX()); 
    int dy = (int) Math.signum(nextPoint.getY() - currentPoint.getY()); 
    return dx != 0 ? (4-heading+dx)%4 : dy != 0 ? (7-heading+dy)%4 : -1; 
} 
+0

因此,您只需保持代碼原樣,因爲它更易於閱讀? – randoms 2011-04-04 16:20:49

+1

這取決於。老實說,我不確定標題和旋轉值0,1,2和3的含義。 – jarnbjo 2011-04-04 16:25:41

+0

標題是機器人朝向哪個方向,0是北,1是東,2南和3是西。旋轉是機器人旋轉到新位置的次數。因此,如果標題爲1(東),新點爲-1x,則該方法應該返回2,以便機器人轉2 * 90,以獲得新的標題。 – randoms 2011-04-04 21:34:53