Nehmen wir an, Sie haben Folgendes:
P1 = (x=2, y=50)
P2 = (x=9, y=40)
P3 = (x=5, y=20)
Angenommen, dies P1
ist der Mittelpunkt eines Kreises. Es ist immer das gleiche. Ich möchte den Winkel, aus dem P2
und besteht P3
, oder mit anderen Worten den Winkel, der neben ist P1
. Der Innenwinkel um genau zu sein. Es wird immer ein spitzer Winkel sein, also weniger als -90 Grad.
Ich dachte: Mann, das ist einfache Geometriemathematik. Aber ich habe jetzt seit ungefähr 6 Stunden nach einer Formel gesucht und finde nur Leute, die über komplizierte NASA-Sachen wie Arccos und Vektor-Skalar-Produkte reden. Mein Kopf fühlt sich an wie in einem Kühlschrank.
Einige Mathe-Gurus hier, die denken, dass dies ein einfaches Problem ist? Ich denke nicht, dass die Programmiersprache hier wichtig ist, aber für diejenigen, die glauben, dass dies der Fall ist: Java und Objective-C. Ich brauche es für beide, habe es aber nicht für diese markiert.
Es wird sehr einfach, wenn Sie es als zwei Vektoren betrachten, einen von Punkt P1 bis P2 und einen von P1 bis P3
also:
a = (p1.x - p2.x, p1.y - p2.y)
b = (p1.x - p3.x, p1.y - p3.y)
Sie können dann die Punktproduktformel umkehren:
um den Winkel zu erhalten:
Denken Sie daran, dass dies nur bedeutet: a1 * b1 + a2 * b2 (hier nur 2 Dimensionen ...)
quelle
Der beste Weg, um mit der Winkelberechnung umzugehen, besteht darin, zu verwenden,
atan2(y, x)
dass bei einem gegebenen Punktx, y
der Winkel von diesem Punkt und derX+
Achse in Bezug auf den Ursprung zurückgegeben wird.Vorausgesetzt, die Berechnung ist
Das heißt, Sie übersetzen die beiden Punkte
-P1
im Grunde genommen durch (mit anderen Worten, Sie übersetzen alles so, dassP1
es im Ursprung endet) und betrachten dann den Unterschied der absoluten Winkel vonP3
und vonP2
.Der Vorteil von
atan2
ist, dass der volle Kreis dargestellt wird (Sie können eine beliebige Zahl zwischen -π und π erhalten), wobei Sie stattdessenacos
mehrere Fälle abhängig von den Vorzeichen behandeln müssen, um das richtige Ergebnis zu berechnen.Der einzige singuläre Punkt für
atan2
ist(0, 0)
... was bedeutet, dass beideP2
undP3
sich von dem unterscheiden müssen,P1
was in diesem Fall keinen Sinn macht, über einen Winkel zu sprechen.quelle
atan2
ist genau das, was für dieses Problem benötigt wird, aber es sieht so aus, als ob die meisten Leute, die zu dieser Frage kommen, einfach nicht lesen oder nicht verstehen können, warum eine aufacos
Lösungen basierende Lösung schlecht ist. Zum Glück habe ich vor vielen Jahren die Phase "Jemand ist im Internet falsch" ( xkcd.com/386 ) verlassen und werde keinen Kampf um die Verteidigung des Offensichtlichen beginnen :-)Lassen Sie mich ein Beispiel in JavaScript geben, damit habe ich viel gekämpft:
Bonus: Beispiel mit HTML5-Canvas
quelle
sqrt
und quadrieren. Siehe meine Antwort hier (geschrieben in Ruby) oder in dieser aktualisierten Demo (JavaScript).Grundsätzlich haben Sie zwei Vektoren, einen Vektor von P1 nach P2 und einen anderen von P1 nach P3. Sie benötigen also nur eine Formel, um den Winkel zwischen zwei Vektoren zu berechnen.
Werfen Sie einen Blick hier für eine gute Erklärung und die Formel.
quelle
Wenn Sie P1 als Mittelpunkt eines Kreises betrachten, denken Sie zu kompliziert. Sie haben ein einfaches Dreieck, sodass Ihr Problem mit dem Kosinusgesetz lösbar ist . Keine Polarkoordinatentransformation oder ähnliches erforderlich. Angenommen, die Abstände sind P1-P2 = A, P2-P3 = B und P3-P1 = C:
Sie müssen lediglich die Länge der Abstände A, B und C berechnen. Diese sind leicht aus den x- und y-Koordinaten Ihrer Punkte und dem Satz von Pythagoras verfügbar
quelle
P1-P2 = A
sollte nicht als "Um A zu berechnen, subtrahiere P2 von P1" gelesen werden, sondern als "Ich definiere A als den Abstand von P1 zu P2", der dann unter Verwendung der zweiten Gleichung berechnet werden kann. Ich wollte nur eine Abkürzung für die Entfernungen definieren, um die Gleichungen besser lesbar zu machen.Ich bin kürzlich auf ein ähnliches Problem gestoßen, nur musste ich zwischen positiven und negativen Winkeln unterscheiden. Für den Fall, dass dies für jemanden von Nutzen ist, empfehle ich das Code-Snippet, das ich aus dieser Mailingliste zum Erkennen der Rotation über ein Touch-Ereignis für Android abgerufen habe:
quelle
Sehr einfache geometrische Lösung mit Erklärung
Vor ein paar Tagen fiel ein in das gleiche Problem und musste mit dem Mathematikbuch sitzen. Ich habe das Problem gelöst, indem ich einige Grundformeln kombiniert und vereinfacht habe.
Betrachten wir diese Zahl.
Wir wollen ϴ wissen , also müssen wir zuerst α und β herausfinden . Nun zu jeder geraden Linie
Sei A = (ax, ay) , B = (bx, by) und O = (ox, oy) . Also für die Linie OA -
In gleicher Weise gilt für die Leitung OB -
Jetzt brauchen wir
ϴ = β - α
. In der Trigonometrie haben wir eine Formel-Nachdem wir den Wert von
tan α
(aus Gleichung-2) undtan b
(aus Gleichung-3) in Gleichung-4 ersetzt und die Vereinfachung angewendet haben, erhalten wirSo,
Das ist es!
Nehmen Sie nun die folgende Abbildung:
Diese C # - oder Java-Methode berechnet den Winkel ( ϴ ) -
quelle
In Objective-C können Sie dies tun, indem Sie
Oder lesen Sie hier mehr
quelle
Sie haben einen vorzeichenbehafteten Winkel (-90) erwähnt. In vielen Anwendungen können Winkel Vorzeichen haben (positiv und negativ, siehe http://en.wikipedia.org/wiki/Angle ). Wenn die Punkte (sagen wir) P2 (1,0), P1 (0,0), P3 (0,1) sind, ist der Winkel P3-P1-P2 herkömmlicherweise positiv (PI / 2), während der Winkel P2-P1- P3 ist negativ. Wenn Sie die Länge der Seiten verwenden, wird nicht zwischen + und - unterschieden. Wenn dies wichtig ist, müssen Sie Vektoren oder eine Funktion wie Math.atan2 (a, b) verwenden.
Winkel können sich auch über 2 * PI hinaus erstrecken, und obwohl dies für die aktuelle Frage nicht relevant ist, war es ausreichend wichtig, dass ich meine eigene Winkelklasse schrieb (auch um sicherzustellen, dass Grad und Bogenmaß nicht verwechselt wurden). Die Frage, ob Winkel1 kleiner als Winkel2 ist, hängt entscheidend davon ab, wie Winkel definiert werden. Es kann auch wichtig sein zu entscheiden, ob eine Linie (-1,0) (0,0) (1,0) als Math.PI oder -Math.PI dargestellt wird
quelle
In letzter Zeit habe auch ich das gleiche Problem ... In Delphi ist es Objective-C sehr ähnlich.
quelle
Hier ist eine C # -Methode, um den Winkel (0-360) gegen den Uhrzeigersinn von der Horizontalen für einen Punkt auf einem Kreis zurückzugeben.
Prost, Paul
quelle
quelle
Es gibt eine einfache Antwort darauf mit High-School-Mathematik.
Angenommen, Sie haben 3 Punkte
Winkel von Punkt A nach B ermitteln
angle = atan2(A.x - B.x, B.y - A.y)
Winkel von Punkt B nach C ermitteln
angle2 = atan2(B.x - C.x, C.y - B.y)
Ich habe diesen Code gerade in dem kürzlich von mir erstellten Projekt verwendet. Ändern Sie das B in P1. Sie können auch das "180 +" entfernen, wenn Sie möchten
quelle
Nun, die anderen Antworten scheinen alles Notwendige abzudecken, daher möchte ich dies nur hinzufügen, wenn Sie JMonkeyEngine verwenden:
Vector3f.angleBetween(otherVector)
da bin ich auf der Suche hierher gekommen :)
quelle
}}
quelle