2014-04-21 122 views
1

我需要確定兩條線段是否相交,但使用line2D.linesIntersect方法時出現問題。該方法返回一個真實結果,即使僅行共享一個終點,就像這樣:Java - 正確的線路交叉檢查

Point2D.Double temp1 = new Point2D.Double(0, 0); 
Point2D.Double temp2 = new Point2D.Double(0, 1); 
Point2D.Double temp3 = new Point2D.Double(1, 0); 

if(Line2D.linesIntersect(temp1.x, temp1.y, temp2.x, temp2.y, temp1.x, temp1.y, temp3.x, temp3.y){ 
    System.out.println("Lines share an endpoint."); 
} 
else{ 
    System.out.println("Lines don't intersect."); 
} 

在這種情況下,我總是得到「線共享一個終點」的消息。當然,在一些線路共享一個端點的情況下,它們可以無限多次相交((0,0)到(0,1)與(0,0)到(0,2))相交) ,這顯然應該返回一個真實的結果。但是,在其他情況下,只有端點被共享,並且沒有其他交叉點發生,程序將無法正常工作。有什麼辦法可以防止這個問題?

回答

2

這是我可以拿出使用我的基礎數學知識的答案。希望它可以幫助你。給定4分,它告訴你兩條線(來自這四個點)是否相交,共享一個端點或者沒有一個。

 //starting point of line 1 
     Point2D.Double temp1 = new Point2D.Double(0 , 1); 
     //ending point of line 1 
     Point2D.Double temp2 = new Point2D.Double(0, -1); 
     //starting point of line 2 
     Point2D.Double temp3 = new Point2D.Double(-1, 0); 
     //ending point of line 2 
     Point2D.Double temp4 = new Point2D.Double(1, 0); 

     //determine if the lines intersect 
     boolean intersects = Line2D.linesIntersect(temp1.x, temp1.y, temp2.x, temp2.y, temp3.x, temp3.y, temp4.x, temp4.y); 

     //determines if the lines share an endpoint 
     boolean shareAnyPoint = shareAnyPoint(temp1, temp2, temp3, temp4); 

     if (intersects && shareAnyPoint) { 
      System.out.println("Lines share an endpoint."); 
     } else if (intersects && !shareAnyPoint) { 
      System.out.println("Lines intersect."); 
     } else { 
      System.out.println("Lines neither intersect nor share a share an endpoint."); 
     } 

這裏是shareAnyPoint(StartPointAEndPointAStartPointBEndPointB)功能,它檢查從任一行開始/結束點位於另一條線路。

public static boolean shareAnyPoint(Point2D.Double A, Point2D.Double B, Point2D.Double C, Point2D.Double D) { 
    if (isPointOnTheLine(A, B, C)) return true; 
    else if (isPointOnTheLine(A, B, D)) return true; 
    else if (isPointOnTheLine(C, D, A)) return true; 
    else if (isPointOnTheLine(C, D, B)) return true; 
    else return false; 
} 

這裏是isPointOnTheLine(StartPoint可以端點MyPoint)函數確定是否點位於行(其他2分制)

public static boolean isPointOnTheLine(Point2D.Double A, Point2D.Double B, Point2D.Double P) { 
    double m = (B.y - A.y)/(B.x - A.x); 

    //handle special case where the line is vertical 
    if (Double.isInfinite(m)) { 
     if(A.x == P.x) return true; 
     else return false; 
    } 

    if ((P.y - A.y) == m * (P.x - A.x)) return true; 
    else return false; 
} 

給它試一試,讓我知道結果。

+0

它正常工作的初始情況下(合法路口),它看起來像它適用於其他情況(A行從(0,0)到(0,1),B行從(0,0)到(-1,0))。我問到這個問題的主要原因是因爲我必須檢查大量可能的線交點以生成鄰接矩陣。它應該是結構化的,不會有兩條線相交。在瞭解到Line2D.linesIntersect函數無法正常工作之前,我瞭解了它的工作原理。 – user3521737

0

如果不侷限於你的Point2D的Line2D對象可以使用JTS(Java的拓撲套件)。

  • 創建行作爲線段形式對象
  • 使用intersects方法

簡單的代碼示例:

LineString lineA = new GeometryFactory().createLineString(new Coordinate[]{new Coordinate(0, 0), new Coordinate(0, 10)}); 
LineString lineB = new GeometryFactory().createLineString(new Coordinate[]{new Coordinate(-5,5), new Coordinate(5,5)}); 
boolean intersect = lineA.intersects(lineB);