首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >我想用python实现三边剖分。我找不到我的功能出了什么问题?

我想用python实现三边剖分。我找不到我的功能出了什么问题?
EN

Stack Overflow用户
提问于 2019-05-09 19:27:47
回答 2查看 627关注 0票数 2

我正在尝试做一个三边测量的实现。Funtion得到了三个3d协助点,以及每个协助点到基站的距离。它必须返回点在3d空间三边测量中的位置。

代码语言:javascript
复制
def trilateration(P1, P2, P3, r1, r2, r3):

  p1 = np.array([0, 0, 0])
  p2 = np.array([P2[0] - P1[0], P2[1] - P1[1], P2[2] - P1[2]])
  p3 = np.array([P3[0] - P1[0], P3[1] - P1[1], P3[2] - P1[2]])
  v1 = p2 - p1
  v2 = p3 - p1

  Xn = (v1)/np.linalg.norm(v1)

  tmp = np.cross(v1, v2)

  Zn = (tmp)/np.linalg.norm(tmp)

  Yn = np.cross(Xn, Zn)

  i = np.dot(Xn, v2)
  d = np.dot(Xn, v1)
  j = np.dot(Yn, v2)

  X = ((r1**2)-(r2**2)+(d**2))/(2*d)
  Y = (((r1**2)-(r3**2)+(i**2)+(j**2))/(2*j))-((i/j)*(X))
  Z1 = np.sqrt(r1**2-X**2-Y**2)
  Z2 = np.sqrt(r1**2-X**2-Y**2)*(-1)

  K1 = P1 + X*Xn + Y * Yn + Z1 * Zn
  K2 = p1 + X * Xn + Y * Yn - Z2 * Zn
  return K1

我有一个测试示例。用这些坐标和距离P1=(2,2,0),P2=(3,3,0),P3=(1,4,0) r1=1,r2=1,r3=1.4142,它应该返回P=(2,3,0)。

但它正在返回3.33253331 1.66746669 1.33373281

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2019-05-09 20:36:26

问题来自给sqrt的表达式,该表达式由于数值不精确而略为负数。这将修复它:

代码语言:javascript
复制
Z1 = np.sqrt(max(0, r1**2-X**2-Y**2))
Z2 = -Z1 

更改这些行可以得到正确的结果:[1.99999361 3.00000639 0.]

注意:如果该点与其他3个点位于同一平面上,则Z值将为0,否则有两种解决方案。此外,为r1r2r3提供精确的值也非常重要,正如@meowgoesthedog所提到的那样。但是,即使使用精确的值,您也需要始终小心浮点不精确,并安全地使用sqrt

票数 0
EN

Stack Overflow用户

发布于 2021-10-15 07:37:59

我没有足够的名气来评论,所以我必须写一个新的答案。

您的代码仍然有一些错误。经过多次测试,我发现K2的计算有一些拼写错误。

完美的函数应该是

代码语言:javascript
复制
def trilateration(P1, P2, P3, r1, r2, r3):

  p1 = np.array([0, 0, 0])
  p2 = np.array([P2[0] - P1[0], P2[1] - P1[1], P2[2] - P1[2]])
  p3 = np.array([P3[0] - P1[0], P3[1] - P1[1], P3[2] - P1[2]])
  v1 = p2 - p1
  v2 = p3 - p1

  Xn = (v1)/np.linalg.norm(v1)

  tmp = np.cross(v1, v2)

  Zn = (tmp)/np.linalg.norm(tmp)

  Yn = np.cross(Xn, Zn)

  i = np.dot(Xn, v2)
  d = np.dot(Xn, v1)
  j = np.dot(Yn, v2)

  X = ((r1**2)-(r2**2)+(d**2))/(2*d)
  Y = (((r1**2)-(r3**2)+(i**2)+(j**2))/(2*j))-((i/j)*(X))
  Z1 = np.sqrt(max(0, r1**2-X**2-Y**2))
  Z2 = -Z2

  K1 = P1 + X * Xn + Y * Yn + Z1 * Zn
  K2 = P1 + X * Xn + Y * Yn + Z2 * Zn
  return K1,K2

两个返回数组是两个可能的位置。

此代码非常有用,因为此答案中的代码是Python形式的https://en.wikipedia.org/wiki/True-range_multilateration#Three_Cartesian_dimensions,_three_measured_slant_ranges,它是3D坐标中三边测量的最简单代码。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/56058383

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档