.. DO NOT EDIT. .. THIS FILE WAS AUTOMATICALLY GENERATED BY SPHINX-GALLERY. .. TO MAKE CHANGES, EDIT THE SOURCE PYTHON FILE: .. "api/gallery/md/thermostats/plot_01_nose_hoover_thermostat.py" .. LINE NUMBERS ARE GIVEN BELOW. .. only:: html .. note:: :class: sphx-glr-download-link-note :ref:`Go to the end ` to download the full example code. .. rst-class:: sphx-glr-example-title .. _sphx_glr_api_gallery_md_thermostats_plot_01_nose_hoover_thermostat.py: The Nose-Hoover thermostat: a friction variable that steers the temperature ============================================================================== Nose's extended system, in Hoover's friction-coefficient form, adds a single dynamical variable :math:`\xi` to Newton's equations: .. math:: \dot{\vec v}_i = \frac{\vec F_i}{m_i} - \xi \vec v_i, \qquad Q\dot\xi = \sum_i m_i v_i^2 - N_f k_B T_0 . When the fluid is too hot, :math:`\xi` grows positive and drains kinetic energy; when it is too cold, :math:`\xi` turns negative and feeds energy back in. A Lennard-Jones fluid started well above the target temperature is run without a thermostat (NVE) and with :class:`~chemistrykit.md.systems.thermostats.NoseHooverThermostat` at two thermostat masses :math:`Q`, recording the temperature and the friction coefficient :math:`\xi`. .. GENERATED FROM PYTHON SOURCE LINES 23-67 .. code-block:: Python import matplotlib.pyplot as plt from chemistrykit.md.systems.lj_fluid import LJFluid from chemistrykit.md.systems.thermostats import NoseHooverThermostat T_target = 1.0 dt, n_steps = 0.004, 5000 def make_hot_fluid(): fluid = LJFluid.from_lattice(n_per_side=6, density=0.6, temperature=T_target, cutoff=2.5, rng=0) fluid.velocities *= 1.8 # start well above the target temperature return fluid fig, axes = plt.subplots(1, 2, figsize=(11, 4.5)) nve = make_hot_fluid() result = nve.run(dt=dt, n_steps=n_steps, sample_every=10) axes[0].plot(result.t, result.temperature, color="gray", label="NVE (no thermostat)") for Q, color in [(5.0, "steelblue"), (50.0, "darkorange")]: fluid = make_hot_fluid() thermostat = NoseHooverThermostat(target_temperature=T_target, Q=Q) times, temps, xis = [], [], [] for _ in range(n_steps // 10): fluid.run(dt=dt, n_steps=10, thermostat=thermostat, sample_every=10) times.append(fluid.t) temps.append(fluid.temperature()) xis.append(thermostat.xi) axes[0].plot(times, temps, color=color, label=f"Nose-Hoover, Q = {Q:g}") axes[1].plot(times, xis, color=color, label=f"Q = {Q:g}") axes[0].axhline(T_target, color="black", linestyle=":", linewidth=0.8, label="target T") axes[0].set_xlabel("t") axes[0].set_ylabel("instantaneous temperature") axes[0].set_title("Temperature") axes[0].legend(loc="upper right") axes[1].axhline(0.0, color="black", linestyle=":", linewidth=0.8) axes[1].set_xlabel("t") axes[1].set_ylabel(r"friction coefficient $\xi$") axes[1].set_title("The extended-system variable") axes[1].legend() fig.tight_layout() .. image-sg:: /api/gallery/md/thermostats/images/sphx_glr_plot_01_nose_hoover_thermostat_001.png :alt: Temperature, The extended-system variable :srcset: /api/gallery/md/thermostats/images/sphx_glr_plot_01_nose_hoover_thermostat_001.png :class: sphx-glr-single-img .. GENERATED FROM PYTHON SOURCE LINES 68-75 Without a thermostat the fluid stays hot. With Nose-Hoover the friction coefficient first rises to cool the fluid, overshoots, and then oscillates about zero, so the temperature swings back and forth around the target rather than being clamped to it; a heavier thermostat mass Q responds more slowly, with longer, gentler swings. Averaged over the second half of each run, the temperature sits close to the target: .. GENERATED FROM PYTHON SOURCE LINES 75-81 .. code-block:: Python for line in axes[0].get_lines()[1:3]: temps = line.get_ydata() print(f"{line.get_label()}: mean T over second half = {sum(temps[len(temps) // 2 :]) / (len(temps) - len(temps) // 2):.3f}") plt.show() .. rst-class:: sphx-glr-script-out .. code-block:: none Nose-Hoover, Q = 5: mean T over second half = 1.000 Nose-Hoover, Q = 50: mean T over second half = 0.999 .. rst-class:: sphx-glr-timing **Total running time of the script:** (0 minutes 4.702 seconds) .. _sphx_glr_download_api_gallery_md_thermostats_plot_01_nose_hoover_thermostat.py: .. only:: html .. container:: sphx-glr-footer sphx-glr-footer-example .. container:: sphx-glr-download sphx-glr-download-jupyter :download:`Download Jupyter notebook: plot_01_nose_hoover_thermostat.ipynb ` .. container:: sphx-glr-download sphx-glr-download-python :download:`Download Python source code: plot_01_nose_hoover_thermostat.py ` .. container:: sphx-glr-download sphx-glr-download-zip :download:`Download zipped: plot_01_nose_hoover_thermostat.zip ` .. only:: html .. rst-class:: sphx-glr-signature `Gallery generated by Sphinx-Gallery `_