【问题标题】:python code to calculate angle between three point using their 3D coordinatespython代码使用它们的3D坐标计算三点之间的角度
【发布时间】:2021-08-01 21:09:44
【问题描述】:

我写了一个代码来使用它们的 3D 坐标计算三个点之间的角度。

import  numpy as np

a = np.array([32.49, -39.96,-3.86])

b = np.array([31.39, -39.28, -4.66])

c = np.array([31.14, -38.09,-4.49])

f = a-b # normalization of vectors
e = b-c # normalization of vectors

angle = dot(f, e) # calculates dot product 
print degrees(cos(angle))  # calculated angle in radians to degree 

代码输出:

degree 33.4118214995

但是当我使用其中一个软件进行计算时,它给出的输出位不同 120 度。请帮忙

参考我写程序时使用的:

(How to calculate bond angle in protein db file?)

【问题讨论】:

  • 1.) 您需要减去相同的点才能获得您正在寻找的向量(请参阅对您其他问题的回答)。 2.) 您必须对向量进行归一化(这不是减法!) 3.) 您还使用了哪些其他软件? 4.) google 提供了 python 脚本,您可以在其中比较您的解决方案。
  • 5.) 您需要使用反余弦函数(acos 或 arccos)。 6.) 你不知道你的代码是做什么的,对吧? :)
  • @kazemakase 是的,在编写代码之前你是对的,我只是按照我添加的参考资料中提到的步骤进行操作,但现在阅读了很多并知道发生了什么。其实我不是数学背景的:)

标签: python math numpy


【解决方案1】:

您的原始代码非常接近。 Adomas.m 的回答不是很地道 numpy:

import numpy as np

a = np.array([32.49, -39.96,-3.86])
b = np.array([31.39, -39.28, -4.66])
c = np.array([31.14, -38.09,-4.49])

ba = a - b
bc = c - b

cosine_angle = np.dot(ba, bc) / (np.linalg.norm(ba) * np.linalg.norm(bc))
angle = np.arccos(cosine_angle)

print np.degrees(angle)

【讨论】:

  • 感谢 Eric 的大力帮助。请解释第 10 行发生了什么(cosine_angle = -----),以及这段代码如何比 adomas.m 更符合 numpy 的习惯。我对python很陌生。谢谢
  • 由于dot 和数组划分而更加惯用,并且因为全局命名空间 (from x import *) 中的所有重要内容通常都不受欢迎。另一个答案中的变量名称不好,除法分布在点积上,所以dot(ba / q, bc / r) == dot(ba, bc) / (q * r),这也有更快的好处
【解决方案2】:

我猜 numpy 已经够用了:

    from numpy import *
    from numpy.linalg import norm
    a = array([32.49, -39.96,-3.86])
    b = array([31.39, -39.28, -4.66])
    c = array([31.14, -38.09,-4.49])
    f = b-a 
    e = b-c 
    abVec = norm(f)
    bcVec = norm(e)
    abNorm = f / abVec;
    bcNorm = e / bcVec;
    res = abNorm[0] * bcNorm[0] + abNorm[1] * bcNorm[1] + abNorm[2] * bcNorm[2];
    angle = arccos(res)*180.0/ pi
    print angle

也可以用点计算res:

    res = abNorm[0] * bcNorm[0] + abNorm[1] * bcNorm[1] + abNorm[2] * bcNorm[2];
    res = dot(abNorm, bcNorm)

【讨论】:

  • 感谢您的更正。如果可能的话,请解释一下 10-13 的行,非常感谢。
  • array([f[0] / abVec, f[1] / abVec, f[2] / abVec]) 拼写更好f / abVec
  • 感谢 Eric...添加回答。
  • jax 第 10-13 行意味着向量 ab 和 bc 被归一化,并找到它们之间的距离,然后在 arccos 的帮助下转换为角度。也许有人有更详细和详尽的解释:)
【解决方案3】:

对于 2D,您可以通过数学库使用此方法。

 import math
 
def getAngle(a, b, c):
    ang = math.degrees(math.atan2(c[1]-b[1], c[0]-b[0]) - math.atan2(a[1]-b[1], a[0]-b[0]))
    return ang + 360 if ang < 0 else ang
 
print(getAngle((5, 0), (0, 0), (0, 5)))

致谢:https://manivannan-ai.medium.com/find-the-angle-between-three-points-from-2d-using-python-348c513e2cd

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-10-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多