Skip to main content

mdanalysis

Comprehensive guide for MDAnalysis - the Python library for analyzing molecular dynamics trajectories. Use for trajectory loading, RMSD/RMSF calculations, distance/angle/dihedral analysis, atom selections, hydrogen bonds, solvent accessible surface area, protein structure analysis, membrane analysis, and integration with Biopython. Essential for MD simulation analysis.

Informations de source

Dépôt
tondevrel/scientific-agent-skills
Dernière activité de la source
1 février 2026 à 04:41
Langue détectée de SKILL.md
anglais
Étoiles
22
Forks
2

Options d'installation

Le prompt qui vérifie d'abord la source est sélectionné par défaut. Vous pouvez passer à une commande directe ou télécharger une copie locale.

Vérifiez les fichiers source

Lisez SKILL.md et les fichiers associés affichés par SkillsMP avant de décider de l'installer.

Affichage de SKILL.md

SKILL.md
Instructions source · Aperçu en lecture seule
name
mdanalysis
description
Comprehensive guide for MDAnalysis - the Python library for analyzing molecular dynamics trajectories. Use for trajectory loading, RMSD/RMSF calculations, distance/angle/dihedral analysis, atom selections, hydrogen bonds, solvent accessible surface area, protein structure analysis, membrane analysis, and integration with Biopython. Essential for MD simulation analysis.
version
2.7
license
GPL-2.0
# MDAnalysis - Molecular Dynamics Analysis Python library for reading, writing, and analyzing molecular dynamics trajectories and structural files. ## When to Use - Loading MD trajectories (DCD, XTC, TRR, NetCDF, etc.) - RMSD and RMSF calculations - Distance, angle, and dihedral analysis - Atom selections (VMD-like syntax) - Hydrogen bond analysis - Solvent Accessible Surface Area (SASA) - Protein secondary structure analysis - Membrane system analysis - Water/ion distribution analysis - Trajectory alignment and fitting - Custom trajectory analysis - Converting between file formats ## Reference Documentation **Official docs**: https://www.mdanalysis.org/docs/ **Search patterns**: `MDAnalysis.Universe`, `MDAnalysis.analysis.rms`, `MDAnalysis.analysis.distances` ## Core Principles ### Use MDAnalysis For | Task | Module | Example | |------|--------|---------| | Load trajectory | `Universe` | `Universe(topology, trajectory)` | | RMSD calculation | `analysis.rms` | `RMSD(mobile, ref)` | | Atom selection | `select_atoms` | `u.select_atoms('protein')` | | Distance analysis | `analysis.distances` | `distance_array(pos1, pos2)` | | H-bond analysis | `analysis.hbonds` | `HydrogenBondAnalysis()` | | SASA calculation | `analysis.sasa` | `SASAnalysis()` | | Contacts analysis | `analysis.contacts` | `Contacts()` | | Trajectory writing | `Writer` | `with Writer() as W` | ### Do NOT Use For - Running MD simulations (use GROMACS, AMBER, NAMD) - Force field calculations (use OpenMM, MDTraj) - Quantum chemistry (use PySCF, Qiskit) - Protein structure prediction (use AlphaFold, RosettaFold) - Initial structure building (use Biopython, PyMOL) ## Quick Reference ### Installation ```bash # pip pip install MDAnalysis # With additional analysis modules pip install MDAnalysis[analysis] # conda conda install -c conda-forge mdanalysis # Development version pip install git+https://github.com/MDAnalysis/mdanalysis.git ``` ### Standard Imports ```python # Core imports import MDAnalysis as mda from MDAnalysis import Universe from MDAnalysis.analysis import rms, align, distances # Common analysis modules from MDAnalysis.analysis.rms import RMSD, RMSF from MDAnalysis.analysis.distances import distance_array from MDAnalysis.analysis.hydrogenbonds.hbond_analysis import HydrogenBondAnalysis from MDAnalysis.analysis.dihedrals import Dihedral # Utilities import numpy as np import matplotlib.pyplot as plt ``` ### Basic Pattern - Load and Analyze ```python import MDAnalysis as mda from MDAnalysis.analysis.rms import RMSD # Load trajectory u = mda.Universe('topology.pdb', 'trajectory.dcd') # Select atoms protein = u.select_atoms('protein') ca_atoms = u.select_atoms('protein and name CA') # Calculate RMSD rmsd_analysis = RMSD(protein, protein, select='backbone') rmsd_analysis.run() # Access results rmsd = rmsd_analysis.results.rmsd print(f"RMSD over time: {rmsd[:, 2]}") # Column 2 is RMSD ``` ### Basic Pattern - Atom Selection ```python import MDAnalysis as mda u = mda.Universe('structure.pdb') # Various selections (VMD-like syntax) protein = u.select_atoms('protein') backbone = u.select_atoms('backbone') ca = u.select_atoms('name CA') resid_10 = u.select_atoms('resid 10') within_5A = u.select_atoms('around 5 resid 10') water = u.select_atoms('resname WAT or resname HOH') print(f"Number of protein atoms: {len(protein)}") print(f"Number of CA atoms: {len(ca)}") ``` ## Critical Rules ### ✅ DO - **Close trajectory files** - Use context managers or close explicitly - **Use atom selections efficiently** - Cache selections for reuse - **Check trajectory length** - Verify n_frames before analysis - **Use vectorized operations** - Leverage NumPy for speed - **Align trajectories** - Align before RMSD calculations - **Handle periodic boundaries** - Use PBC-aware distance calculations - **Validate atom groups** - Check empty selections - **Use appropriate frames** - Slice trajectories if needed - **Save intermediate results** - Don't recompute expensive calculations - **Check units** - MDAnalysis uses Angstroms and picoseconds ### ❌ DON'T - **Load entire trajectory in memory** - Stream through frames - **Ignore PBC** - Always consider periodic boundary conditions - **Forget to align** - RMSD without alignment is meaningless - **Use wrong atom names** - Check topology for correct names - **Mix coordinate systems** - Be consistent with units - **Ignore missing atoms** - Handle incomplete residues - **Recompute unnecessarily** - Cache expensive calculations - **Use string selections in loops** - Parse once, reuse - **Forget to unwrap coordinates** - Handle molecules split by PBC - **Ignore memory limits** - Process large trajectories in chunks ## Anti-Patterns (NEVER) ```python import MDAnalysis as mda import numpy as np # ❌ BAD: Loading entire trajectory in memory u = mda.Universe('top.pdb', 'traj.dcd') all_coords = [] for ts in u.trajectory: all_coords.append(u.atoms.positions.copy()) all_coords = np.array(all_coords) # Huge memory usage! # ✅ GOOD: Process frame by frame u = mda.Universe('top.pdb', 'traj.dcd') for ts in u.trajectory: # Process current frame coords = u.atoms.positions # Do analysis... # Move to next frame automatically # ❌ BAD: RMSD without alignment rmsd_values = [] for ts in u.trajectory: rmsd = rms.rmsd(mobile.positions, reference.positions) rmsd_values.append(rmsd) # Wrong! Not aligned! # ✅ GOOD: Align before RMSD from MDAnalysis.analysis.rms import RMSD R = RMSD(mobile, reference, select='backbone') R.run() rmsd_values = R.results.rmsd[:, 2] # ❌ BAD: Creating selection in loop for ts in u.trajectory: ca = u.select_atoms('name CA') # Parsed every frame! # Do something with ca # ✅ GOOD: Create selection once ca = u.select_atoms('name CA') for ts in u.trajectory: # Use ca (automatically updated each frame) positions = ca.positions # ❌ BAD: Ignoring periodic boundaries distance = np.linalg.norm(atom1.position - atom2.position) # ✅ GOOD: PBC-aware distance from MDAnalysis.lib.distances import distance_array dist = distance_array( atom1.position[np.newaxis, :], atom2.position[np.newaxis, :], box=u.dimensions )[0, 0] # ❌ BAD: Not checking for empty selections selection = u.select_atoms('resname XYZ') # Continue without checking if selection is empty! avg_pos = selection.center_of_mass() # May crash! # ✅ GOOD: Validate selections selection = u.select_atoms('resname XYZ') if len(selection) == 0: print("Warning: No atoms found matching selection") else: avg_pos = selection.center_of_mass() ``` ## Loading Trajectories (Universe) ### Basic Universe Creation ```python import MDAnalysis as mda # Single structure file u = mda.Universe('protein.pdb') # Topology + trajectory u = mda.Universe('topology.pdb', 'trajectory.dcd') # Multiple trajectories (concatenated) u = mda.Universe('top.pdb', 'traj1.dcd', 'traj2.dcd', 'traj3.dcd') # Different formats u = mda.Universe('system.gro', 'traj.xtc') # GROMACS u = mda.Universe('system.psf', 'traj.dcd') # CHARMM/NAMD u = mda.Universe('system.prmtop', 'traj.nc') # AMBER # From memory (numpy arrays) coords = np.random.rand(100, 3) # 100 atoms, xyz u = mda.Universe.empty(100, trajectory=True) u.atoms.positions = coords print(f"Number of atoms: {len(u.atoms)}") print(f"Number of frames: {len(u.trajectory)}") print(f"Total time: {u.trajectory.totaltime} ps") ``` ### Trajectory Information ```python import MDAnalysis as mda u = mda.Universe('topology.pdb', 'trajectory.dcd') # Trajectory properties traj = u.trajectory print(f"Number of frames: {traj.n_frames}") print(f"Time step: {traj.dt} ps") print(f"Total time: {traj.totaltime} ps") # Current frame info print(f"Current frame: {traj.frame}") print(f"Current time: {traj.time} ps") print(f"Box dimensions: {u.dimensions}") # [a, b, c, alpha, beta, gamma] # Iterate through frames for i, ts in enumerate(u.trajectory): if i >= 5: break print(f"Frame {ts.frame}: time = {ts.time:.2f} ps") # Jump to specific frame u.trajectory[100] # Go to frame 100 print(f"Now at frame: {u.trajectory.frame}") # Slice trajectory for ts in u.trajectory[::10]: # Every 10th frame print(f"Frame {ts.frame}") ``` ### Working with Multiple Trajectories ```python import MDAnalysis as mda # Load multiple trajectory files u = mda.Universe('top.pdb', 'part1.dcd', 'part2.dcd', 'part3.dcd') print(f"Total frames from all trajectories: {len(u.trajectory)}") # Or use ChainReader explicitly from MDAnalysis.coordinates.chain import ChainReader trajectories = ['part1.dcd', 'part2.dcd', 'part3.dcd'] u = mda.Universe('top.pdb', trajectories, continuous=True) # Access frame indices for i, ts in enumerate(u.trajectory[::100]): print(f"Global frame {i}: actual frame {ts.frame}, time {ts.time:.2f}") ``` ## Atom Selections ### Basic Selection Syntax ```python import MDAnalysis as mda u = mda.Universe('system.pdb') # Protein selections protein = u.select_atoms('protein') backbone = u.select_atoms('backbone') # N, CA, C mainchain = u.select_atoms('backbone or name O') # Specific residues resid_10 = u.select_atoms('resid 10') resid_range = u.select_atoms('resid 10:20') resid_list = u.select_atoms('resid 10 15 20 25') # Residue names water = u.select_atoms('resname WAT or resname HOH') ions = u.select_atoms('resname NA or resname CL') # Atom names ca_atoms = u.select_atoms('name CA') hydrogens = u.select_atoms('name H*') # Wildcards # By element carbons = u.select_atoms('element C') # Segments seg_a = u.select_atoms('segid A') print(f"Protein atoms: {len(protein)}") print(f"Water molecules: {len(water)}") print(f"CA atoms: {len(ca_atoms)}") ``` ### Advanced Selections ```python import MDAnalysis as mda u = mda.Universe('protein_solvent.pdb') # Geometric selections around_10 = u.select_atoms('around 5.0 protein') # Within 5Å of protein within_box = u.select_atoms('prop x < 50 and prop y < 50') # Spatial queries resid_10 = u.select_atoms('resid 10') near_res10 = u.select_atoms('around 10.0 resid 10 and not resid 10') # Combining selections hydrophobic = u.select_atoms( 'resname ALA or resname VAL or resname LEU or ' 'resname ILE or resname PHE or resname TRP or resname MET' ) charged = u.select_atoms( 'resname ARG or resname LYS or resname ASP or resname GLU' ) # Boolean operations not_protein = u.select_atoms('not protein') protein_no_h = u.select_atoms('protein and not name H*') # By property high_bfactor = u.select_atoms('protein and prop beta > 50') # SMARTS matching (requires RDKit) # aromatic = u.select_atoms('smarts c1ccccc1') print(f"Hydrophobic residues: {len(hydrophobic)}") print(f"Charged residues: {len(charged)}") ``` ### Dynamic Selections ```python import MDAnalysis as mda u = mda.Universe('topology.pdb', 'trajectory.dcd') # Regular selection (static) protein = u.select_atoms('protein') # Dynamic selection (updated each frame) # Example: Select water within 3.5Å of protein water_near_protein = u.select_atoms( 'resname WAT and around 3.5 protein', updating=True ) # Track number of nearby water molecules over time water_counts = [] for ts in u.trajectory: # water_near_protein automatically updates water_counts.append(len(water_near_protein)) print(f"Water molecules near protein per frame:") print(f" Min: {min(water_counts)}") print(f" Max: {max(water_counts)}") print(f" Mean: {sum(water_counts)/len(water_counts):.1f}") # Another example: ions near active site active_site = u.select_atoms('resid 100:110') nearby_ions = u.select_atoms( '(resname NA or resname CL) and around 8.0 resid 100:110', updating=True ) for i, ts in enumerate(u.trajectory[::10]):
Voir sur GitHub
Ce SKILL.md est tres volumineux, SkillsMP affiche donc ici seulement la premiere section. Voir sur GitHub