En utilisant la solution d'une équation différentielle dans deux commandes de tracé séparé dans Mathematica

StackOverflow https://stackoverflow.com/questions/1327789

Question

Je l'ai rencontré un problème en essayant d'utiliser la réponse d'un NDSolve dans deux commandes parcelle séparée. Pour illustrer le problème, je vais utiliser une équation différentielle simple et une seule commande plot. Si je vous écris quelque chose comme ceci:

{Plot[x[t], {t, 0, 10}], x[4]} 
/. NDSolve[{x'[s] == - x[s], x[0] == 1}, x, {s, 0, 10}]

Il permet de résoudre l'équation et calcule x [4] sans problème, mais l'intrigue tourne vide, et je ne sais pas pourquoi.

Dans mon problème réel, mon équation est un système assez complexe pour plusieurs fonctions, et au lieu de x [4] Je dessine un tracé paramétrique des fonctions résolues. Je compte finalement d'inclure tout cela dans un Manipulez déclaration donc je ne veux pas le NDSolve déclaration à apparaître plus d'une fois (prend trop de temps) et je ne peux pas seulement calculer à l'avance (car il a beaucoup de paramètres).


Edit: Je voudrais clarifier et d'élargir ma question: Ce que je veux vraiment faire est d'inclure ma déclaration de traçage dans un Manipulez Déclaration de la manière suivante:

Manipulate[{Plot[x[t], {t, 0, 10}], x[4]} 
/. NDSolve[{x'[s] == - a*x[s], x[0] == 1}, x, {s, 0, 10}]
,{{a,1},0,5}]

Depuis que la déclaration Manipulez donne une valeur au paramètre a , je ne peux pas calculer la réponse à la NDSolve au préalable. En outre, étant donné que mon système d'équations réelle est très complexe et non linéaire, je ne peux pas utiliser la fonction symbolique DSolve .

Désolé si on ne savait pas avant.

Était-ce utile?

La solution

Votre problème est que Plot [] fait des choses drôles pour faire tracer plus pratique, et l'une des choses qu'il fait est tout simplement pas tracer des choses qu'il ne peut pas évaluer numériquement. Donc, dans l'expression que vous avez publié,

Plot[x[t], {t, 0, 10}]

va juste avant et évalue avant faire la substitution de la règle avec la solution de NDSolve, la production d'un objet graphique d'une parcelle vide. Cet objet graphique contient aucune référence à x, donc il n'y a rien à remplacer.

Vous voulez vous assurer que la substitution se fait avant le tracé. Si vous voulez également vous assurer que la substitution peut se faire en plusieurs endroits, vous voulez stocker la solution dans une variable.

sol = NDSolve[{x'[s] == - x[s], x[0] == 1}, x, {s, 0, 10}];
{Plot[Evaluate[x[t] /. sol], {t, 0, 10}], x[4] /. sol} 

Évaluation [] dans le terrain fait en sorte que Mathematica une seule fois la substitution, au lieu d'une fois pour chaque point de parcelle. Il est pas important pour un simple substitution de règles comme celui-ci, mais il est une bonne habitude de l'utiliser dans le cas où vous voulez jamais tracer quelque chose de plus compliqué.


Pour faire ce travail dans un Manipuler, la méthode simple consiste à utiliser avec [], qui est l'une des constructions de portée de Mathematica; il est celui à utiliser où vous voulez juste de remplacer quelque chose sans l'utiliser comme variable que vous pouvez muter.

Par exemple,

Manipulate[
  With[{sol = NDSolve[{x'[s] == - x[s], x[0] == 1}, x, {s, 0, 10}]},
    {Plot[x[t] /. sol // Evaluate, {t, 0, 10}, PlotRange -> {0, 1}], 
     x[4] /. sol}],
  {{a, 1}, {0, 5}}]

Utilisez l'option PlotRange afin de maintenir l'axe des y fixe; sinon les choses vont sauter d'une manière laide que la valeur d'un changement. Lorsque vous faites des choses plus complexes avec Manipulez, il y a un certain nombre d'options pour contrôler la vitesse des mises à jour, ce qui peut être important si votre ODE est assez compliquée qu'il faut un certain temps à résoudre.

Autres conseils

Pendant ce temps, j'ai trouvé une autre façon de le faire. Il est moins élégant, mais il utilise une seule substitution donc j'ai pensé que je vais le poster ici aussi.

L'idée est d'utiliser Maintenez Terrain il ne s'évalué, faire la substitution de la règle, puis sur ReleaseHold , juste avant la balise Manipulez .

Manipulate[ReleaseHold[
  Hold[ {Plot[x[t], {t, 0, 10}, PlotRange -> {0, 1}], x[4]} ]
 /.NDSolve[{x'[s] == -a x[s], x[0] == 1}, x, {s, 0, 10}]
], {{a, 1}, 0, 5}]
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top