Metadata-Version: 2.4
Name: mars-epr
Version: 0.0.5.post4
Summary: A library for computation CW and time resolved spectra
Author-email: Arkady Samsonenko <a.samsonenko@tomo.nsc.ru>, Ivan Kurganskii <kurgansky@tomo.nsc.ru>
License-Expression: MIT
Project-URL: Homepage, https://github.com/ArkadySamsonenkoWork/MaRs
Project-URL: Telegram, https://t.me/Arkady_Samsonenko
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.8
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Operating System :: OS Independent
Requires-Python: >=3.8
Description-Content-Type: text/markdown
Requires-Dist: numpy>=1.19.4
Requires-Dist: torch>=2.2
Requires-Dist: scipy>=1.15
Requires-Dist: scikit-learn
Requires-Dist: torchdiffeq
Requires-Dist: PyWavelets
Requires-Dist: matplotlib
Requires-Dist: safetensors
Requires-Dist: seaborn
Provides-Extra: opt
Requires-Dist: optuna>=4.3; extra == "opt"
Requires-Dist: nevergrad>=1.0.12; extra == "opt"
Requires-Dist: optuna_dashboard; extra == "opt"
Provides-Extra: plot
Requires-Dist: seaborn; extra == "plot"
Requires-Dist: plotly; extra == "plot"
Requires-Dist: matplotlib; extra == "plot"

# MaRs

**A toolkit for researchers to simulate, analyze, and explore EPR systems efficiently.**

---

## 🚀 Overview

**MaRs** is a Python library for constructing spin systems (electrons and nuclei), defining their magnetic interactions, and simulating Electron Paramagnetic Resonance (EPR) spectra.
It supports a wide range of interaction models, efficient batched computations on CPU and GPU, flexible numerical precision (`float32` / `float64`), and tools for both stationary and time-resolved EPR experiments.


## 🔑 Core Capabilities

### Interaction Support
MaRs allows users to construct spin systems with the most widely used magnetic interactions:
- Zeeman interaction  
- Exchange interaction  
- Dipolar interaction  
- Zero-field splitting (ZFS)  
- Hyperfine interaction  

Both **isotropic** and **anisotropic** parameters are supported.

---

### Orientation Support
- Arbitrary orientation of interaction tensors using **Euler angles**

---

### Broadening Support
MaRs provides several mechanisms to model experimental linewidths:
- Gaussian and Lorentzian line broadening  
- Hamiltonian broadening  
- Broadening due to distributions of Hamiltonian parameters  (so-called strains)

---

### EPR Spectroscopy Simulation
- Simulation of **continuous-wave (CW) EPR spectra**
- Support for **powder** and **single-crystal** samples
- Field-domain and frequency-domain simulations

---

### Spin-Polarized Spectra Support
- Simulation of stationary EPR spectra with arbitrary **non-equilibrium (spin-polarized) initial populations**, in addition to standard thermal (Boltzmann) populations
- Polarization can be specified directly in any of the supported bases (e.g. eigenbasis, ZFS basis, multiplet basis, product basis, triplet xyz basis, Zeeman basis, or a custom basis), with automatic transformation into the working basis

---

### Radiation Polarization Support
- Simulation of spectra under polarized microwave radiation
- Polarization-dependent transition probabilities
- Supports crystalline and powder samples under linear, circular, and unpolarized excitation

---


### Numerical Precision Control
- Support for `float64` and `float32` precision

---

### CPU / CUDA Support
- Support execution on **CPU** and **CUDA-enabled GPUs**
---

### Optimization Framework
- Parameter fitting using **Optuna** and **Nevergrad** libraries
---

### Post-Fitting Analysis
- Tools for analyzing alternative solutions
- Exploration of parameter correlations and degeneracies

---

# ⏱️ Time-Resolved Capabilities

MaRs is a comprehensive framework for modeling time-resolved EPR experiments with two complementary computational approaches.

### Relaxation Approaches
- **Population relaxation (Kinetic approach)**: Evolution of diagonal density matrix elements (population vectors)
- **Density matrix relaxation**: Full evolution of all density matrix elements. It includes two methods of computations:
  - Rotating frame approximation method
  - Direct propagator calculation method

---

### Flexible Relaxation Parameters Definition
MaRs provides powerful tools for defining complex relaxation processes:
- **Population losses** (e.g., phosphorescence from triplet states)
- **Spontaneous transitions** (thermal transitions satisfying detailed balance)
- **Induced transitions** (driven transitions not satisfying detailed balance)
- **Dephasing** (for density matrix formalism)

All mechanisms can be specified in any of several predefined bases or custom transformation matrices.

---

### Relaxation Formalisms: Lindblad and Bloch-Redfield
MaRs provides three complementary ways to define relaxation, which can be freely combined within a single simulation:

- **Lindblad formalism**: relaxation is defined phenomenologically from Lindblad jump-operator form.
- **Bloch-Redfield formalism**: relaxation rates are derived microscopically from system-bath coupling operators and a spectral density function. Users define the coupling operator as a matrix together with the spectral density function (as an explicit function of frequency).
- **Custom relaxation superoperators**: for relaxation processes that fall outside both formalisms, users can supply a fully custom relaxation superoperator directly.

Thermal balance (detailed balance) is automatically enforced for the thermal parts of all three formalisms, and the Lindblad, Bloch-Redfield, and custom contributions can be summed together into a single total relaxation superoperator (or kinetic matrix).

---

### Basis Transformation Framework
Comprehensive support for relaxation parameter specification in multiple bases:
- **Eigenbasis** (`eigen`): Hamiltonian eigenstates in magnetic field
- **Zero-field splitting basis** (`zfs`): Eigenstates of the ZFS operator
- **Multiplet basis** (`multiplet`): Total spin and projection states |S, M⟩
- **Product basis** (`product`): Individual spin projections |ms1, ms2, ..., msk, is1, ..., ism⟩
- **Triplet xyz basis** (`xyz`): Tx, Ty, Tz basis used for triplet molecules
- **Zeeman** (`zeeman`): Basis in high magnetic field
- **Custom bases**: User-defined transformation matrices

Automatic transformation of kinetic matrices and relaxation superoperators between bases.

---

### Relaxation Algebra
- **Summation**: Combine multiple relaxation mechanisms defined in different bases
- **Multiplication**: Construct relaxation mechanism of interacting spin centers
- **Concatenation**: Construct relaxation mechanism of isolated sub-systems.
---

### Liouville Space Formalism
- Full support for Liouvillian relaxation superoperators
- Implementation via **Lindblad equation** for general Markovian evolution
- Automatic enforcement of detailed balance for spontaneous transitions
---

### Numerical Solvers
Multiple solution strategies optimized for different scenarios:

**Population kinetics:**
- Stationary solution via matrix exponentiation (for time-independent systems)
- Quasi-stationary iterative solution (for time-dependent rates)
- Adaptive ODE integration (via `torchdiffeq`, for general time dependence)

**Density matrix evolution:**
- Rotating frame approximation (computationally efficient, limited to isotropic or close to isotropic g-factors)
- Propagator computation approach (fully general, supports arbitrary anisotropy and relaxation)

---

## ▶️ Getting Started

### Installation

```bash
git clone https://github.com/ArkadySamsonenkoWork/MaRs.git
cd mars
pip install -e <folder>
```
or just
```bash
pip install mars-epr
```

### Code Example
```bash


import torch
import matplotlib.pyplot as plt
from mars import spin_model, spectra_manager

# Select device and precision
device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
dtype = torch.float64

# Define a simple electron spin system
g_tensor = spin_model.Interaction((2.02, 2.04, 2.06), dtype=dtype, device=device)

system = spin_model.SpinSystem(
    electrons=[0.5],
    g_tensors=[g_tensor],
    dtype=dtype,
    device=device
)

# Create a powder sample
sample = spin_model.MultiOrientedSample(
    base_spin_system=system,
    gauss=0.001,
    lorentz=0.001,
    dtype=dtype,
    device=device
)

# Create spectrum calculator
spectra = spectra_manager.StationarySpectra(
    freq=9.8e9,
    sample=sample,
    dtype=dtype,
    device=device
)

# Magnetic field range
fields = torch.linspace(0.3, 0.4, 1000, device=device, dtype=dtype)

# Compute spectrum
intensity = spectra(sample, fields)

# Plot result
plt.plot(fields.cpu(), intensity.cpu())
plt.xlabel("Magnetic field (T)")
plt.ylabel("Intensity (a.u.)")
plt.title("Simulated CW EPR Spectrum")
plt.show()

```
