¿Por qué mi modelo de dos cuerpos no funciona? [cerrado]

He creado un modelo simple de partículas de dos cuerpos de 1 dimensión en C++. En el modelo, la partícula 1 comienza en la posición (0,0) y la partícula 2 comienza en la posición (1,0). Las partículas se aceleran una hacia la otra a una velocidad proporcional a la distancia que las separa.

El código me parece bien, pero los resultados parecen muy bazar y completamente no físicos. Sospecho que el problema puede estar relacionado con los pasos de tiempo discreto tomados. He intentado hacer que la tasa de aceleración sea proporcional a la distancia ^ 2 y los resultados no parecen más realistas.

Aquí está el código y los resultados:

ingrese la descripción de la imagen aquí

ingrese la descripción de la imagen aquí

El gráfico anterior es una Posición vs. Gráfico de tiempo.

¿Cómo puedo ajustar el código para obtener resultados más razonables?

Creo que deberías agregar en tu pregunta lo que esperas que suceda. Me parece que "acelerado el uno hacia el otro a un ritmo proporcional a la distancia entre ellos" significa que debería ser un oscilador armónico. ¿¿Es eso correcto??
También sugeriría comentar tu código ...
Pero en el código tienes que la aceleración es proporcional a 1 d (Mire específicamente su definición de dv1dt).
@Jared, la gravedad es proporcional a 1/d^2, pero la gravedad se comporta como un oscilador armónico. Creo que 1/d también debería hacerlo. Sin embargo, 1/d^2 también da resultados extraños.
La gravedad (específicamente la gravedad newtoniana como parece que lo estás haciendo) no es un oscilador armónico.
@Jared, sí, técnicamente no, pero el movimiento es oscilatorio con una amplitud máxima. Mi gráfico muestra claramente que la amplitud aumenta (y disminuye) por todas partes. Oscilatorio armónico o no, los resultados no parecen coincidir con el código.
Vale la pena señalar que la gravedad, definida por la Ecuación de Poisson , conduce a órbitas inestables en 1D o 2D (conduce a soluciones estables en 3D... y creo que otras... pero estoy retrocediendo demasiado en mi Mecánica Clásica clase para realmente dar un buen comentario aquí).
¿ Sería la ciencia computacional un mejor hogar para esta pregunta?
@Qmechanic No lo sé. No estoy familiarizado con ese foro, pero ciertamente no creo que esto sea apropiado para StackOverflow o el foro de Ciencias de la Computación. Todavía soy de la opinión de que hay una buena razón para los resultados recibidos (que no tiene que ver con el caos o la computación).
@Qmechanic: estoy de acuerdo con Jared: se trata de métodos numéricos para la física. Si bien la integración numérica es algo que estudian los no físicos, las técnicas necesarias para abordar esto deberían ser de interés para esta comunidad. La respuesta actualmente aceptada no hace justicia a la pregunta ...
Iba a ser desagradable y escribir una respuesta wiki comunitaria desagradable. En cambio, seré desagradable en un comentario y diré que este código es horrible.
No debe abrir y cerrar manualmente el archivo; utilizar RAII.
Voto para cerrar esta pregunta como fuera de tema porque se trata de depurar un programa y no de física. Quizás Computational Science podría ser más adecuado para este programa.

Respuestas (2)

En situaciones como esta, es una buena idea ajustar el paso de tiempo en función del gradiente de la fuerza, porque todo el concepto de integración numérica es que "las cosas no cambian demasiado desde ahora hasta el siguiente paso de tiempo", y esa suposición se viola cuando te mueves rápidamente a través de una región con una fuerza que cambia rápidamente.

Esto tiene un efecto secundario arriesgado: si hace que el paso de tiempo sea "lo suficientemente pequeño" para hacer frente a la variación rápida, y la variación se vuelve "infinitamente rápida", su algoritmo puede "atascarse": puede encontrarse con la paradoja de Xeno de la Aquiles y la tortuga.

Para evitar quedarse atascado, algunas integraciones numéricas (como Runge-Kutta) son mejores para tener en cuenta la curvatura de orden superior, lo que permite un paso más grande sin perder precisión.

Sin embargo, en su caso, la aceleración para el próximo paso de tiempo completo está determinada por la posición actual, por lo que si sus partículas están cerca unas de otras al comienzo del paso, serán arrojadas lejos, y dado que su fuerza de atracción entonces se verán muy disminuidos, les será difícil volver.

Algunas críticas a tu código:

  1. Tú defines particle1[4]pero solo usas dos componentes
  2. Codificas el paso de tiempo en lugar de usar una variable comodt
  3. Usas el método de integración más básico... por favor aprende sobre otros
  4. Usted define implícitamente masa = 1 y constante de fuerza = 1; considere hacer esas variables (incluso si las establece en 1)

Con respecto al primer punto, usaría a structpara mis partículas:

typedef struct{
  double x;
  double v;
} PARTICLE;

y luego puedes acceder a sus propiedades con

PARTICLE p1, p2;
p1.v = 0.;
p1.x = 0.;
p2.v = 0.;
p2.x = 1.;

Lo cual es inmediatamente más legible... Si desea trabajar en dos dimensiones, puede escribirlas explícitamente como parte de su struct: ( double x; double y; double vx; double vy;) o convertirlas en matrices.

Pero en realidad, los pasos de tiempo variables y las interpolaciones de mayor orden ayudarían con la estabilidad de su solución.

Gracias, diste en el clavo de lo que está mal con el programa. Gracias por tus consejos también, estoy empezando en métodos numéricos.
Escribir un simulador que se comporte bien es difícil. Pero las recompensas son increíbles a medida que aprendes todo lo que hay que saber. Está en el paso uno y esta respuesta lo lleva a través de los pasos 2, 3 y 4. Cuanto más trabaje, más matices abordará y lo llevará a través de los pasos 5...12. Has obtenido un doctorado en este momento.

Estás obteniendo partículas que tienen una distancia de 0 entre sí y, por lo tanto, tienen una aceleración infinita. La computadora no puede resolver esto, por lo que explota según lo cerca que esté el paso de cero.

No estoy seguro de cuál sería el comportamiento "físico", dado que las masas puntuales de distancia cero son difíciles de estudiar. Pero si agregó una coordenada y y le dio una velocidad inicial, podría obtener mejores resultados (básicamente, una elipse alargada en lugar de una línea oscilante).

Puede hacer que la velocidad y inicial sea muy pequeña, de modo que se aproxime al movimiento X. O tal vez solo agregue una pequeña compensación a su división.

No es teoría del caos si es una anomalía informática.
Si quieres "teoría del caos", entonces puedes mirar mi siguiente animación donde esto forma una "luna". Cada esfera compuesta está compuesta de bolas distribuidas al azar y a veces obtienes una luna y otras veces no (por casualidad grabé una de las veces en que se formó una luna, que, con mi ajuste fino, es alrededor de 1 en 10 carreras).
Pot-a-to, pot-ah-to. De todos modos, el término teoría del caos no está bien definido. Pero lo que quiero decir es que pequeños cambios en las condiciones iniciales provocan grandes cambios en la producción.
No, el término caos se define muy claramente. Significa que dadas las mismas condiciones iniciales, ligeras variaciones conducen a resultados drásticamente diferentes.
Entonces, si el OP cambia su paso de tiempo, ¿la oscilación cambia drásticamente? ;-)
Estoy bromeando. Tienes razón, por supuesto. Pero el punto es que el cálculo está mal definido debido al error de dividir por cero que debería ocurrir si el paso de tiempo fuera correcto.
Bueno, hay algo con lo que estamos de acuerdo... Nunca debes permitir que las partículas puntuales, bajo ninguna fuerza, colisionen a una distancia "casi cero".
Esto no es "teoría del caos". El problema de los dos cuerpos no es caótico. Esto es simplemente malas matemáticas.
El problema de los dos cuerpos no es caótico, pero hay que mantener una distancia positiva entre ellos.
El problema no es caótico, pero el enfoque de la solución es... en otras palabras, mediante el uso de un paso de tiempo fijo, el OP convirtió un problema no caótico en uno caótico (es decir, sensible a pequeñas desviaciones en la entrada). "Vamos a llamar todo el asunto fuera."