Quelle est la différence entre atan et atan2 en C ++?


157

Quelle est la différence entre atanet atan2en C ++?

Réponses:



322

Des mathématiques scolaires, nous savons que la tangente a la définition

tan(α) = sin(α) / cos(α)

et nous différencions quatre quadrants en fonction de l'angle que nous fournissons aux fonctions. Le signe du sin, coset tanont la relation suivante (où nous négligeons les multiples exacts de π/2):

  Quadrant    Angle              sin   cos   tan
-------------------------------------------------
  I           0    < α < π/2      +     +     +
  II          π/2  < α < π        +     -     -
  III         π    < α < 3π/2     -     -     +
  IV          3π/2 < α < 2π       -     +     -

Étant donné que la valeur de tan(α)est positive, on ne peut pas distinguer si l'angle provenait du premier ou du troisième quadrant et s'il est négatif, il pourrait provenir du deuxième ou du quatrième quadrant. Donc, par convention, atan()renvoie un angle du premier ou du quatrième quadrant (c'est-à-dire -π/2 <= atan() <= π/2), quelle que soit l'entrée d'origine de la tangente.

Afin de récupérer toutes les informations, nous ne devons pas utiliser le résultat de la division sin(α) / cos(α)mais nous devons regarder les valeurs du sinus et du cosinus séparément. Et c'est ce que atan2()fait. Il prend à la fois le sin(α)et cos(α)et résout les quatre quadrants en ajoutant πau résultat de atan()chaque fois que le cosinus est négatif.

Remarque: La atan2(y, x)fonction prend en fait a yet un xargument, qui est la projection d'un vecteur avec longueur vet angle αsur les axes y et x, ie

y = v * sin(α)
x = v * cos(α)

ce qui donne la relation

y/x = tan(α)

Conclusion: atan(y/x) on retient certaines informations et on ne peut que supposer que l'entrée provenait des quadrants I ou IV. En revanche, atan2(y,x)obtient toutes les données et peut ainsi résoudre l'angle correct.


3
Un petit détail, la plage -π/2 <= atan() <= π/2comprend en fait un point ( pi/2) du quadrant II.
Z boson du

28

Une autre chose à mentionner est qu'il atan2est plus stable lors du calcul des tangentes en utilisant une expression comme atan(y / x)et xest 0 ou proche de 0.


Intéressant, avez-vous une source pour cela? Est-ce vrai en général ou juste pour C ++?
Gerard

26

Les valeurs réelles sont en radians mais pour les interpréter en degrés, ce sera:

  • atan = donne une valeur d'angle entre -90 et 90
  • atan2 = donne une valeur d'angle entre -180 et 180

Pour mon travail qui implique le calcul de divers angles tels que le cap et le relèvement en navigation, atan2dans la plupart des cas fait le travail.


12

atan (x) Renvoie la valeur principale de l'arc tangente de x, exprimée en radians.

atan2 (y, x) Renvoie la valeur principale de l'arc tangente de y / x, exprimée en radians.

Notez qu'en raison de l'ambiguïté du signe, une fonction ne peut pas déterminer avec certitude dans quel quadrant l'angle tombe uniquement par sa valeur tangente (atan seul). Vous pouvez utiliser atan2 si vous avez besoin de déterminer le quadrant.


3
atan2 (x, y) -> atan2 (y, x)
yesraaj

La plage des valeurs principales est (-pi,pi]mais atan2 a la plage [-pi,pi]donc il inclut une valeur supplémentaire -pid'une autre branche due à atan2(-0.0,x)for x<0.
Z boson

4

Je suppose que la question principale essaie de comprendre: "quand dois-je utiliser l'un ou l'autre", ou "que dois-je utiliser", ou "est-ce que j'utilise le bon"?

Je suppose que le point important est que atan était uniquement destiné à alimenter des valeurs positives dans une courbe de direction vers la droite comme pour les vecteurs temps-distance. Cero est toujours en bas à gauche, et les thigs ne peuvent monter que vers la droite, juste plus lentement ou plus vite. atan ne renvoie pas de nombres négatifs, vous ne pouvez donc pas tracer les choses dans les 4 directions sur un écran simplement en ajoutant / soustrayant son résultat.

atan2 est destiné à ce que l'origine soit au milieu, et les choses peuvent reculer ou descendre. C'est ce que vous utiliseriez dans une représentation à l'écran, car la direction dans laquelle vous voulez que la courbe ait une importance n'a pas d'importance. Donc atan2 peut vous donner des nombres négatifs, car son cero est au centre, et son résultat est quelque chose que vous pouvez utiliser pour tracer les choses dans 4 directions.


2

Avec atan2, vous pouvez déterminer le quadrant comme indiqué ici .

Vous pouvez utiliser atan2 si vous avez besoin de déterminer le quadrant.


2

Prenons un triangle rectangle. Nous étiquetons l'hypoténuse r, le côté horizontal y et le côté vertical x. L'angle d'intérêt α est l'angle entre x et r.

C ++ atan2(y, x)nous donnera la valeur de l'angle α en radians. atanest utilisé si nous ne connaissons ou ne sommes intéressés que par y / x et non par y et x individuellement. Donc, si p = y / x, alors pour obtenir α, nous utiliserions atan(p).

Vous ne pouvez pas utiliser atan2pour déterminer le quadrant, vous ne pouvez l'utiliser atan2que si vous savez déjà dans quel quadrant vous vous trouvez! En particulier, x et y positifs impliquent le premier quadrant, y positif et x négatif, le second et ainsi de suite. atanou atan2eux - mêmes renvoient simplement un nombre positif ou négatif, rien de plus.


4
Si tout ce que vous avez, c'est que p=y/xvous pouvez toujours utiliser atan2(p,1).
Mark Ransom

0

Mehrwolf ci-dessous est correct, mais voici une heuristique qui peut aider:

Si vous travaillez dans un système de coordonnées à 2 dimensions, ce qui est souvent le cas pour la programmation de la tangente inverse, vous devez absolument utiliser atan2. Il donnera la gamme complète d'angles de 2 pi et s'occupera des zéros dans la coordonnée x pour vous.

Une autre façon de dire cela est que atan (y / x) est pratiquement toujours faux. N'utilisez atan que si l'argument ne peut pas être considéré comme y / x.


0

atan2(y,x)est généralement utilisé si vous souhaitez convertir des coordonnées cartésiennes en coordonnées polaires. Il vous donnera l'angle, tandis que sqrt(x*x+y*y)ou, si disponible, hypot(y,x)vous donnera la taille.

atan(x)est simplement l'inverse de tan. Dans le cas ennuyeux que vous devez utiliser atan(y/x)parce que votre système ne fournit pas atan2, vous devrez faire des vérifications supplémentaires pour les signes de xet y, et pour x=0, afin d'obtenir le bon angle.

Remarque: atan2(y,x) est défini pour toutes les valeurs réelles de yet x, sauf pour le cas où les deux arguments sont nuls.


0

En atan2, la sortie est: -pi< atan2(y,x)< pi
et atan, la sortie est: -pi/2< atan(y/x)< pi/2 // il dose pas considérer le trimestre.
Si vous souhaitez obtenir l'orientation entre 0et 2*pi(comme les mathématiques du lycée), nous devons utiliser atan2 et pour les valeurs négatives, ajoutez le 2*pipour obtenir le résultat final entre 0et 2*pi.
Voici le code source Java pour l'expliquer clairement:

System.out.println(Math.atan2(1,1)); //pi/4 in the 1st quarter
System.out.println(Math.atan2(1,-1)); //(pi/4)+(pi/2)=3*(pi/4) in the 2nd quarter

System.out.println(Math.atan2(-1,-1 ));//-3*(pi/4) and it is less than 0.
System.out.println(Math.atan2(-1,-1)+2*Math.PI); //5(pi/4) in the 3rd quarter

System.out.println(Math.atan2(-1,1 ));//-pi/4 and it is less than 0.
System.out.println(Math.atan2(-1,1)+2*Math.PI); //7*(pi/4) in the 4th quarter

System.out.println(Math.atan(1 ));//pi/4
System.out.println(Math.atan(-1 ));//-pi/4
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.