.. DO NOT EDIT. .. THIS FILE WAS AUTOMATICALLY GENERATED BY SPHINX-GALLERY. .. TO MAKE CHANGES, EDIT THE SOURCE PYTHON FILE: .. "fitting/2D_fitting/plot_1_LHistidine_PASS.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_fitting_2D_fitting_plot_1_LHistidine_PASS.py: ¹³C 2D MAT NMR of L-Histidine ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ .. GENERATED FROM PYTHON SOURCE LINES 7-9 The following is an illustration for fitting 2D MAT/PASS datasets. The example dataset is a :math:`^{13}\text{C}` 2D MAT spectrum of L-Histidine from Walder `et al.` [#f1]_ .. GENERATED FROM PYTHON SOURCE LINES 9-22 .. code-block:: Python import numpy as np import csdmpy as cp import matplotlib.pyplot as plt from lmfit import Minimizer from mrsimulator import Simulator from mrsimulator.method.lib import SSB2D from mrsimulator import signal_processor as sp from mrsimulator.utils import spectral_fitting as sf from mrsimulator.utils import get_spectral_dimensions from mrsimulator.utils.collection import single_site_system_generator .. GENERATED FROM PYTHON SOURCE LINES 24-26 Import the dataset ------------------ .. GENERATED FROM PYTHON SOURCE LINES 26-36 .. code-block:: Python host = "https://ssnmr.org/sites/default/files/mrsimulator/" filename = "1H13C_CPPASS_LHistidine.csdf" mat_dataset = cp.load(host + filename) # For the spectral fitting, we only focus on the real part of the complex dataset. mat_dataset = mat_dataset.real # Convert the coordinates along each dimension from Hz to ppm. _ = [item.to("ppm", "nmr_frequency_ratio") for item in mat_dataset.dimensions] .. GENERATED FROM PYTHON SOURCE LINES 37-39 When using the SSB2D method, ensure the horizontal dimension of the dataset is the isotropic dimension. Here, we apply an appropriate transpose operation to the dataset. .. GENERATED FROM PYTHON SOURCE LINES 39-54 .. code-block:: Python mat_dataset = mat_dataset.T # transpose # plot of the dataset. max_amp = mat_dataset.max() levels = (np.arange(24) + 1) * max_amp / 25 # contours are drawn at these levels. options = dict(levels=levels, alpha=0.75, linewidths=0.5) # plot options plt.figure(figsize=(8, 3.5)) ax = plt.subplot(projection="csdm") ax.contour(mat_dataset, colors="k", **options) ax.set_xlim(180, 15) plt.grid() plt.tight_layout() plt.show() .. image-sg:: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_001.png :alt: plot 1 LHistidine PASS :srcset: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_001.png :class: sphx-glr-single-img .. GENERATED FROM PYTHON SOURCE LINES 55-56 Estimate noise statistics from the dataset .. GENERATED FROM PYTHON SOURCE LINES 56-72 .. code-block:: Python coords = mat_dataset.dimensions[0].coordinates # noise_region = np.where(np.logical_and(coords > 65e-6, coords < 110e-6)) noise_region = np.where(np.logical_and(coords < 110e-6, coords > 65e-6)) noise_data = mat_dataset[noise_region] plt.figure(figsize=(3.75, 2.5)) ax = plt.subplot(projection="csdm") ax.imshow(noise_data, aspect="auto", interpolation="none") plt.title("Noise section") plt.axis("off") plt.tight_layout() plt.show() noise_mean, sigma = noise_data.mean(), noise_data.std() noise_mean, sigma .. image-sg:: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_002.png :alt: Noise section :srcset: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_002.png :class: sphx-glr-single-img .. rst-class:: sphx-glr-script-out .. code-block:: none (, ) .. GENERATED FROM PYTHON SOURCE LINES 73-78 Create a fitting model ---------------------- **Guess model** Create a guess list of spin systems. .. GENERATED FROM PYTHON SOURCE LINES 78-90 .. code-block:: Python shifts = [120, 128, 135, 175, 55, 25] # in ppm zeta = [-70, -65, -60, -60, -10, -10] # in ppm eta = [0.8, 0.4, 0.9, 0.3, 0.05, 0.05] spin_systems = single_site_system_generator( isotope="13C", isotropic_chemical_shift=shifts, shielding_symmetric={"zeta": zeta, "eta": eta}, abundance=100 / 6, ) .. GENERATED FROM PYTHON SOURCE LINES 91-94 **Method** Create the SSB2D method. .. GENERATED FROM PYTHON SOURCE LINES 94-106 .. code-block:: Python # Get the spectral dimension parameters from the experiment. spectral_dims = get_spectral_dimensions(mat_dataset) PASS = SSB2D( channels=["13C"], magnetic_flux_density=9.395, # in T rotor_frequency=1500, # in Hz spectral_dimensions=spectral_dims, experiment=mat_dataset, # add the measurement to the method. ) .. GENERATED FROM PYTHON SOURCE LINES 107-108 **Guess Spectrum** .. GENERATED FROM PYTHON SOURCE LINES 108-139 .. code-block:: Python # Simulation # ---------- sim = Simulator(spin_systems=spin_systems, methods=[PASS]) sim.run() # Post Simulation Processing # -------------------------- processor = sp.SignalProcessor( operations=[ # Lorentzian convolution along the isotropic dimensions. sp.FFT(dim_index=0), sp.apodization.Exponential(FWHM="50 Hz"), sp.IFFT(dim_index=0), sp.Scale(factor=2122600), ] ) processed_dataset = processor.apply_operations(dataset=sim.methods[0].simulation).real # Plot of the guess Spectrum # -------------------------- plt.figure(figsize=(8, 3.5)) ax = plt.subplot(projection="csdm") ax.contour(mat_dataset, colors="k", **options) ax.contour(processed_dataset, colors="r", linestyles="--", **options) ax.set_xlim(180, 15) plt.grid() plt.tight_layout() plt.show() .. image-sg:: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_003.png :alt: plot 1 LHistidine PASS :srcset: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_003.png :class: sphx-glr-single-img .. GENERATED FROM PYTHON SOURCE LINES 140-144 Least-squares minimization with LMFIT ------------------------------------- Use the :func:`~mrsimulator.utils.spectral_fitting.make_LMFIT_params` for a quick setup of the fitting parameters. .. GENERATED FROM PYTHON SOURCE LINES 144-147 .. code-block:: Python params = sf.make_LMFIT_params(sim, processor) print(params.pretty_print(columns=["value", "min", "max", "vary", "expr"])) .. rst-class:: sphx-glr-script-out .. code-block:: none Name Value Min Max Vary Expr SP_0_operation_1_Exponential_FWHM 50 -inf inf True None SP_0_operation_3_Scale_factor 2.123e+06 -inf inf True None sys_0_abundance 16.67 0 100 True None sys_0_site_0_isotropic_chemical_shift 120 -inf inf True None sys_0_site_0_shielding_symmetric_eta 0.8 0 1 True None sys_0_site_0_shielding_symmetric_zeta -70 -inf inf True None sys_1_abundance 16.67 0 100 True None sys_1_site_0_isotropic_chemical_shift 128 -inf inf True None sys_1_site_0_shielding_symmetric_eta 0.4 0 1 True None sys_1_site_0_shielding_symmetric_zeta -65 -inf inf True None sys_2_abundance 16.67 0 100 True None sys_2_site_0_isotropic_chemical_shift 135 -inf inf True None sys_2_site_0_shielding_symmetric_eta 0.9 0 1 True None sys_2_site_0_shielding_symmetric_zeta -60 -inf inf True None sys_3_abundance 16.67 0 100 True None sys_3_site_0_isotropic_chemical_shift 175 -inf inf True None sys_3_site_0_shielding_symmetric_eta 0.3 0 1 True None sys_3_site_0_shielding_symmetric_zeta -60 -inf inf True None sys_4_abundance 16.67 0 100 True None sys_4_site_0_isotropic_chemical_shift 55 -inf inf True None sys_4_site_0_shielding_symmetric_eta 0.05 0 1 True None sys_4_site_0_shielding_symmetric_zeta -10 -inf inf True None sys_5_abundance 16.67 0 100 False 100-sys_0_abundance-sys_1_abundance-sys_2_abundance-sys_3_abundance-sys_4_abundance sys_5_site_0_isotropic_chemical_shift 25 -inf inf True None sys_5_site_0_shielding_symmetric_eta 0.05 0 1 True None sys_5_site_0_shielding_symmetric_zeta -10 -inf inf True None None .. GENERATED FROM PYTHON SOURCE LINES 148-149 **Solve the minimizer using LMFIT** .. GENERATED FROM PYTHON SOURCE LINES 149-160 .. code-block:: Python opt = sim.optimize() # Pre-compute transition pathways minner = Minimizer( sf.LMFIT_min_function, params, fcn_args=(sim, processor, sigma), fcn_kws={"opt": opt}, ) result = minner.minimize() result .. raw:: html

Fit Result



.. GENERATED FROM PYTHON SOURCE LINES 161-163 The best fit solution --------------------- .. GENERATED FROM PYTHON SOURCE LINES 163-175 .. code-block:: Python best_fit = sf.bestfit(sim, processor)[0].real # Plot of the best fit solution plt.figure(figsize=(8, 3.5)) ax = plt.subplot(projection="csdm") ax.contour(mat_dataset, colors="k", **options) ax.contour(best_fit, colors="r", linestyles="--", **options) ax.set_xlim(180, 15) plt.grid() plt.tight_layout() plt.show() .. image-sg:: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_004.png :alt: plot 1 LHistidine PASS :srcset: /fitting/2D_fitting/images/sphx_glr_plot_1_LHistidine_PASS_004.png :class: sphx-glr-single-img .. GENERATED FROM PYTHON SOURCE LINES 176-180 .. [#f1] B. J. Walder, K. K. Dey, D. C. Kaseman, J. H. Baltisberger, and P. J. Grandinetti, Sideband separation experiments in NMR with phase incremented echo train acquisition, J. Phys. Chem. 2013, **138**, 174203-1-12. `DOI: 10.1063/1.4803142 `_ .. rst-class:: sphx-glr-timing **Total running time of the script:** (0 minutes 25.399 seconds) .. _sphx_glr_download_fitting_2D_fitting_plot_1_LHistidine_PASS.py: .. only:: html .. container:: sphx-glr-footer sphx-glr-footer-example .. container:: sphx-glr-download sphx-glr-download-jupyter :download:`Download Jupyter notebook: plot_1_LHistidine_PASS.ipynb ` .. container:: sphx-glr-download sphx-glr-download-python :download:`Download Python source code: plot_1_LHistidine_PASS.py ` .. only:: html .. rst-class:: sphx-glr-signature `Gallery generated by Sphinx-Gallery `_