2

给定以下系统:

在此处输入图像描述

在哪里:

  • A: 存在于rxz 平面上半径为圆的边缘上任意位置的点。
  • θ:正x轴与从原点到点的向量之间的角度A。这应该在 -PI/2 到 PI/2 的范围内。
  • B1:圆与正 x 轴相交处高度为 的点h1
  • B2:圆与正 z 轴相交处高度为 的点h2
  • d1B1:和之间的距离A
  • d2B2:和之间的距离A

假设:

  • h1, h2, 和r是已知常数。
  • d1并且d2是已知变量。

我如何找到θ

这最终将在嵌入式系统中用 C 语言实现,在该系统中,我对arctan2sinecosine. 因此,性能绝对是一个优先事项,如果它们正确到小数点后 3 位(这是我的三角函数的准确度),就可以使用估计。

然而,即使给出了一个数学算法,我相信我可以制定出具体的实现。

对于它的价值,我得到了大约:

(d1^2 - h1^2) / r = (sin(θ))^2        + (cos(θ))^2
(d2^2 - h2^2) / r = (sin(PI/4 - θ))^2 + (cos(PI/4 - θ))^2

在我意识到这一点之前,从数学上讲,这超出了我的范围。

4

2 回答 2

3

这不是一个完整的答案,而是一个开始。

您可以进行两个简单的简化。

让 H1 和 H2 成为平面中 B1 和 B2 下方的点。由于您知道 h1 和 d1、h2 和 d2,您可以计算 2 个距离 A-H1 和 A-H2(使用毕达哥拉斯)。现在您已将拼图简化为平面。

此外,您实际上不需要同时查看 H1 和 H2。给定距离 A-H1,A 只有 2 个可能的位置,它们在 x 轴上镜像。然后你可以通过查看 A-H2 距离是高于还是低于阈值距离 H2-H1 来找出两者中的哪一个。

这似乎是一个好的开始:-)

于 2013-07-11T23:07:56.050 回答
1

使用@Rhialto,对角落案例进行额外的简化和测试:

// c1 is the signed chord distance A to (B1 projected to the xz plane)
// c1*c1 + h1*h1 = d1*d1
// c1 = +/- sqrt(d1*d1 - h1*h1)  (choose sign later)
// c1 = Cord(r, theta) = fabs(r*2*sin(theta/2))
// theta = asin(c1/(r*2))*2
//
// theta is < 0 when d2 > sqrt(h2*h2 + sqrt(2)*r*sqrt(2)*r)
// theta is < 0 when d2 > sqrt(h2*h2 + 2*r*r)
// theta is < 0 when d2*d2 > h2*h2 + 2*r*r

#define h1 (0.1)
#define h2 (0.25)
#define r (1.333)

#define h1Squared (h1*h1)
#define rSquared  (r*r)
#define rSquaredTimes2  (r*r*2)
#define rTimes2   (r*2)
#define d2Big (h2*h2 + 2*r*r)

// Various steps to avoid issues with d1 < 0, d2 < 0, d1 ~= h1 and theta near pi
double zashu(double d1, double d2) {
  double c1Squared = d1*d1 - h1Squared;
  if (c1Squared < 0.0)
    c1Squared = 0.0;  // _May_ be needed when in select times |d1| ~= |h1|
  double a = sqrt(c1Squared) / rTimes2;
  double theta = (a <= 1.0) ? asin(a)*2.0 : asin(1.0)*2.0; // Possible a is _just_ greater than 1.0
  if (d2*d2 > d2Big) // this could be done with fabs(d2) > pre_computed_sqrt(d2Big)
    theta = -theta;
  return theta;
}
于 2013-08-12T22:24:56.180 回答