Wir können einen radialen Linien-Sweep durchführen, um das Problem zu lösen -
Sortieren Sie die Endpunkte der Liniensegmente nach dem Winkel, in dem die Linie verbunden ist P und der Endpunkt Q machen, brechen Krawatten wrt Abstand von P. Wenn wir nun radial (im Uhrzeigersinn) fegen, behalten wir zwei Arten von Ereignissen bei: "Öffnen" und "Schließen", die dem Öffnen und Schließen eines neuen Liniensegments entsprechen. Verfolgen Sie, wie viele Liniensegmente zu einem bestimmten Zeitpunkt "aktiv" sind ("aktiv" bedeutet, dass wir auf den Endpunkt gestoßen sind, der dem "offenen" Ereignis des Liniensegments entspricht, aber nicht auf den anderen Endpunkt im noch fegen). Wenn wir zu irgendeinem Zeitpunkt genau ein 'aktives' Liniensegment haben, ist dieses Segment von sichtbarP.
Wir sollten darauf achten, dass wir zu Beginn des Sweeps immer bei einem „offenen“ Event beginnen.
Es wird____geben 2nSolche Ereignisse und das Verfolgen der Anzahl aktiver Segmente können in konstanter Zeit pro Segment durchgeführt werden (über eine Hash-Tabelle oder eine Logarithmus-Zeit unter Verwendung einer ausgeglichenen BST). Daher ist der dominierende Schritt in diesem Algorithmus die Sortierung, die dauertO(n) Zeit nach Bedarf.
Wie bei allen Problemen mit der rechnerischen Geometrie kann es einige Eckfälle geben, die ich übersehen habe, aber die allgemeine Vorstellung, dass wenn zu einem bestimmten Zeitpunkt während des radialen Liniendurchlaufs genau ein aktives Liniensegment vorhanden ist, es von sichtbar ist P ist der springende Punkt, um dieses Problem zu lösen.