C++ N体模拟不起作用

C++ N体模拟不起作用,c++,C++,我正试图编写一个代码来解决n体问题,当使用一个包含所有体的数组而不是单独使用不同的体时,我遇到了麻烦。我目前不知道我的代码出了什么问题,但当我用y的函数为任何物体绘制x时,我得到了一条直线,这显然是不对的 这是我当前的代码: #include <cstdlib> #include <iostream> #include <cmath> #include <fstream> #define h 10000.0 #define N 3 #defin

我正试图编写一个代码来解决n体问题,当使用一个包含所有体的数组而不是单独使用不同的体时,我遇到了麻烦。我目前不知道我的代码出了什么问题,但当我用y的函数为任何物体绘制x时,我得到了一条直线,这显然是不对的

这是我当前的代码:

#include <cstdlib>
#include <iostream>
#include <cmath>
#include <fstream>
#define h  10000.0
#define N  3
#define G  6.67384*pow(10.0,-11)

using namespace std;



class particle{
      public:
      double kx1,kx2,kx3,kx4, kv1, kv2, kv3, kv4;
      double ky1, ky2, ky3, ky4, kvy1, kvy2, kvy3, kvy4;
      double x,y,vx,vy,m;


      double dist(particle aap){
             double dx = x - aap.x;
             double dy = y - aap.y;
             return sqrt(pow(dx,2.0)+pow(dy,2.0));
             }

      double g(double x1, double y1,particle aap){
             return G*aap.m*(aap.x-x1)/pow(dist(aap),3.0);
             }

      double p(double x1, double y1, particle aap){
             return G*aap.m*(aap.y-y1)/pow(dist(aap),3.0);
       }


      void update(){                                      //object advances 1 step
           x = x + (1/6.0)*(kx1+2*kx2+2*kx3+kx4);
           vx = vx + (1/6.0)*(kv1+2*kv2+2*kv3+kv4);
           y = y + (1/6.0)*(ky1+2*ky2+2*ky3+ky4);
           vy = vy + (1/6.0)*(kvy1+2*kvy2+2*kvy3+kvy4);
           }

     void create(double x1, double y1, double vx1, double vy1, double m1){
                      x = x1;
                      y = y1;
                      vx = vx1;
                      vy = vy1;
                      m =m1;
                      }

     bool operator ==(particle &other){
          if(x == other.x && y == other.y && vx == other.vx && vy == other.vy){
               return true;
               }
               }

      };




particle bodies[N];



void set(particle (&bodies)[N]){
     bodies[0].create(1, 1, -2, 1, 2*pow(10.0,30));
     bodies[1].create(2870671*pow(10.0,6), 0, 0, 6800, 8.6810*pow(10.0,25));
     bodies[2].create(4498542*pow(10.0,6),0 ,0, 5430, 1.0243*pow(10.0,26));
     }


double xforce(double x1, double y1, particle aap, particle bodies[N]){    //force in the x- direction

       double fx = 0;
       for (int i = 0; i <= N; i++){
           if (bodies[i] == aap ){;}

           else{
                fx += aap.g(x1,y1,bodies[i]);
                }
                }
       return fx;
       }

double yforce(double x1, double y1, particle aap, particle bodies[N]){ //force in the y- direction 

       double fy = 0;
       for (int i = 0; i <= N; i++){
           if (bodies[i] == aap) {;}

           else{
                fy += aap.p(x1,y1,bodies[i]);
                }
                }
       return fy;
       }


void corr(double t, particle bodies[N]){                            //runge kutta 4
     for(int i =0; i <= N; i++){

            bodies[i].kx1 = t*bodies[i].vx;
            bodies[i].kv1 = t*xforce(bodies[i].x, bodies[i].y, bodies[i], bodies);
            bodies[i].ky1 = t*bodies[i].vy;
            bodies[i].kvy1 = t*yforce(bodies[i].x, bodies[i].y, bodies[i], bodies);

            bodies[i].kx2 = t*(bodies[i].vx + 0.5*bodies[i].kv1);
            bodies[i].kv2 = t*xforce(bodies[i].x + 0.5*bodies[i].kx1, bodies[i].y + 0.5*bodies[i].ky1, bodies[i], bodies);
            bodies[i].ky2 = t*(bodies[i].vy + 0.5*bodies[i].kvy1);
            bodies[i].kvy2 = t*yforce(bodies[i].x + 0.5*bodies[i].kx1, bodies[i].y + 0.5*bodies[i].ky1, bodies[i], bodies);

            bodies[i].kx3 = t*(bodies[i].vx+ 0.5*bodies[i].kv2);
            bodies[i].kv3 = t*xforce(bodies[i].x + 0.5*bodies[i].kx2, bodies[i].y + 0.5*bodies[i].ky2, bodies[i], bodies);
            bodies[i].ky3 = t*(bodies[i].vy+ 0.5*bodies[i].kvy2);
            bodies[i].kvy3 = t*yforce(bodies[i].x + 0.5*bodies[i].kx2, bodies[i].y + 0.5*bodies[i].ky2,bodies[i], bodies);

            bodies[i].kx4 = t*(bodies[i].vx + bodies[i].kv3);
            bodies[i].kv4 = t*xforce(bodies[i].x+ bodies[i].kx3, bodies[i].y + bodies[i].ky3, bodies[i], bodies);
            bodies[i].ky4 = t*(bodies[i].vy + bodies[i].kvy3);
            bodies[i].kvy4 = t*yforce(bodies[i].x + bodies[i].kx3, bodies[i].y + bodies[i].ky3, bodies[i], bodies);
            }
     }


void calculate(particle (&bodies)[N]){
     set(bodies);
     ofstream file;
     file.open("tester.txt");
     for(int i =0; i <=50000; i++){

             corr(h, bodies);                          
             for(int j = 0; j <= N; j++){
                     bodies[j].update();
                     }                   
             if( i%1000 == 0){

                 file << i*h;
                 for(int j = 0; j <=N ; j++){
                          file <<"  "<<bodies[j].x << "  "<< bodies[j].y;
                          }
                 file <<"  "<<"\n";
                 }
             else{;}
             }
     file.close();
     }


int main()
{   
    calculate(bodies);
    system("pause");
    return 0;
}
#包括
#包括
#包括
#包括
#定义h 10000.0
#定义n3
#定义G 6.67384*功率(10.0,-11)
使用名称空间std;
类粒子{
公众:
双kx1、kx2、kx3、kx4、kv1、kv2、kv3、kv4;
双ky1、ky2、ky3、ky4、kvy1、kvy2、kvy3、kvy4;
双x,y,vx,vy,m;
双距离(粒子aap){
双dx=x-aap.x;
双dy=y-aap.y;
返回sqrt(pow(dx,2.0)+pow(dy,2.0));
}
双g(双x1,双y1,粒子aap){
返回G*aap.m*(aap.x-x1)/pow(距离(aap),3.0);
}
双p(双x1,双y1,粒子aap){
返回G*aap.m*(aap.y-y1)/pow(距离(aap),3.0);
}
void update(){//对象前进1步
x=x+(1/6.0)*(kx1+2*kx2+2*kx3+kx4);
vx=vx+(1/6.0)*(kv1+2*kv2+2*kv3+kv4);
y=y+(1/6.0)*(ky1+2*ky2+2*ky3+ky4);
vy=vy+(1/6.0)*(kvy1+2*kvy2+2*kvy3+kvy4);
}
创建空洞(双x1、双y1、双vx1、双vy1、双m1){
x=x1;
y=y1;
vx=vx1;
vy=vy1;
m=m1;
}
布尔运算符==(粒子和其他){
如果(x==other.x&&y==other.y&&vx==other.vx&&vy==other.vy){
返回true;
}
}
};
粒子体[N];
空隙集(粒子和实体)[N]){
实体[0]。创建(1,1,-2,1,2*pow(10.0,30));
body[1]。创建(2870671*pow(10.0,6),0,06800,8.6810*pow(10.0,25));
实体[2]。创建(4498542*pow(10.0,6),0,05430,1.0243*pow(10.0,26));
}
双x力(双x1,双y1,粒子aap,粒子体[N]){//x方向的力
双fx=0;

对于(int i=0;i首先,所有的
i你可能都在经历,因为RK4不是,n体问题是a。我在尝试将RK4用于太阳系n体时也遇到了同样的问题。你也遇到了。你应该尝试另一种辛数值方法,如Euler、Verlet或order辛积分器。

好的,我解决了这个问题,但那是sn不是唯一的问题,我仍然得到直线。不过谢谢你的输入。
std::vector body(3)有什么问题
虽然对于3个元素,使用数组会更好,而且速度也会更快,因为这样可以避免一级间接寻址。问题是我无法编写std::vector body;我在其中定义了数组body。我得到了错误“在‘为什么不尝试避免全局创建它并在
main()中创建它’之前,需要构造函数、析构函数或类型转换”
相反?并通过引用将向量传递给使用它的函数。对于固定大小的数组
std::array
避免了
std::vector
的间接性,同时仍然提供边界检查功能。引用的代码是一个不好的示例,因为它没有实现RK4的合理和正确版本。是的,能量漂移不是一个问题可以作废,但看起来不像一阶方法那么快(赛博煎蛋饼代码实际上就是如此)