用向量模拟行星轨道

3
为了更好地理解向量的工作原理,我正在尝试创建一个非常简单的模拟,模拟地球绕太阳运动。目前,我只想让地球在圆形轨道上绕太阳运动,不考虑任何物理定律。
我以为我的做法会有效,但实际上它创造了一种类似于斐波那契螺旋线的运动。
// initial positions
vec2 sun(0.0,0.0);
vec2 earth(10.0,0.0);

while(true) {

    vec2 earthToSun = normalize(sun - earth); // this is the vector 'pointing from the earth towards the sun'
    vec2 speedVector = vec2(-earthToSun.y, earthToSun.x); // this is the vector perpendicular to the earthToSun vector

    earth = earth + earthToSun + speedVector; // move the earth along the resulting vector

}

我的计算错在哪里?

当我看到那个标签时,我就知道它不可能是你用它的目的。 - chris
尝试使用0.0、10.0等浮点数代替整数。 - HAL9000
earth = earth + earthToSun + speedVector; 将地球向太阳方向移动1个单位,并向垂直方向移动1个单位。这不是一个圆形轨道。 - nullptr
@Inspired 我理解了。我认为这就是我们太阳系中行星运动的方式?行星有一个特定的速度向量,但重力使它沿椭圆轨道运动。将速度向量乘以某个标量因子可以使地球绕太阳转更长一段时间。这让我想知道地球是否会和太阳“碰撞”。 - RaptorDotCpp
给定一个时间量t,以及给定太阳的位置、地球的位置和地球速度,您可以通过以下方式近似计算新的地球位置和速度:加速度=K*normalize(太阳-地球);地球=地球+地球速度*t+加速度*t*t/2.0;地球速度=地球速度+t*加速度,其中K是某个常数。但由于模拟的离散性质,地球很快就会撞上太阳(或者飘走)。 - nullptr
显示剩余4条评论
2个回答

3

为什么不用三角函数来解决这个问题:

#define PI 3.1415926
float r = 10.0;
for (int theta=0; theta<2*PI; theta += 0.01)
{
    float x = r*cos(theta),
          y = r*sin(theta);
    earth = vec2(x, y);
}

显然,根据需要更改期间、theta的起始值、增量等。


我已经按照这种方式创建了模拟,但我的目标是最终基于牛顿和开普勒的定律,并创建更加逼真的模拟。为此,我需要向量。我还想熟悉向量数学。 - RaptorDotCpp
@RaptorDotCpp 好的,这些定律 从角度/角速度方面分析行星运动。试图添加向量可能是错误的方法,因为它必然会使地球沿着轨道的切线移动。只有当您的步长 -> 0 时,才能得到正确的轨道。三角学方法实际上可能更容易扩展以包括实际的定律。 - Matt Phillips

1
你的初始条件应该是:
vec2 sun(0.0,0.0);
vec2 earth(10.0,0.0);
vec2 speedVector = vec2(-earthToSun.y, earthToSun.x);

看起来不错。但是你的方程式有两个问题。

  1. 您的地球位置应该随时间变化如下:

    vec2 earthToSun = normalize(sun - earth);
    earth = earth + earthToSun;  // 这里没有添加speedVector
    

    请注意,我在更新代码中没有向地球添加speedVector。你所做的是在整个模拟过程中加速了地球。

  2. 您的normalize函数必须通过平方距离进行标准化。我不确定您是如何实现的。 F = g m1 m2 / r ^ 2。 我怀疑您的normalize只除以了r,而不是r ^ 2。请参考https://en.wikipedia.org/wiki/Gravitational_constant

你的地球不一定会按照圆形轨道运行,很可能是椭圆形轨道。此外,请确保选择足够小的步长。每次迭代中,earth 只应该改变其到太阳距离的一小部分,否则你将累积明显的积分误差。

不幸的是,结果是一样的(当然除了速度慢之外)。 - RaptorDotCpp
earth = earth + earthToSun; 这行代码会让地球掉进太阳里。 - nullptr

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接