pyMCR: Multivariate Curve Resolution in Python¶

GitHub Repository: https://www.github.com/usnistgov/pyMCR

Documentation available online at https://pages.nist.gov/pyMCR

Software DOI: https://doi.org/10.18434/M32064

Manuscript DOI: https://doi.org/10.6028/jres.124.018

pyMCR is a small package for performing multivariate curve resolution. Currently, it implements a simple alternating regression scheme (MCR-AR). The most common implementation is with ordinary least-squares regression, MCR-ALS.

MCR with non-negativity constraints on both matrices is the same as nonnegative matrix factorization (NMF). Historically, other names were used for MCR as well:

• Self modeling mixture analysis (SMMA)

• Self modeling curve resolution (SMCR)

Available methods¶

• Regressors:

• Constraints

• Non-negativity

• Normalization

• Zero end-points

• Zero (approx) end-points of cumulative summation (can specify nodes as well)

• Non-negativity of cumulative summation

• Compress or cut values above or below a threshold value

• Replace sum-across-features samples (e.g., 0 concentration) with prescribed target

• Enforce a plane (“planarize”). E.g., a concentration image is a plane.

• Error metrics / Loss function

• Mean-squared error

• Other options

• Fix known targets (C and/or ST, and let others vary)

Software Design Philosophy¶

What it does do:

• Approximate the concentration and spectral matrices via minimization routines. This is the core the MCR methods.

• Enable the application of certain constraints in a user-defined order.

What it does not do:

• Estimate the number of components in the sample (though some tools tools may be provided in the future). This is a bonus feature in some more-advanced MCR-ALS packages.

Logging¶

New in pyMCR 0.3.1, Python’s native logging module is now used to capture messages. Though this is not as convenient as print() statements, it has many advantages.

A simple example that prints simplified logging messages to the stdout (command line):

```import sys
import logging

# Need to import pymcr or mcr prior to setting up the logger
from pymcr.mcr import McrAR

logger = logging.getLogger('pymcr')
logger.setLevel(logging.DEBUG)

# StdOut is a "stream"; thus, StreamHandler
stdout_handler = logging.StreamHandler(stream=sys.stdout)

# Set the message format. Simple and removing log level or date info
stdout_format = logging.Formatter('%(message)s')  # Just a basic message akin to print statements
stdout_handler.setFormatter(stdout_format)

# Begin your code for pyMCR below
```

Basic Usage¶

```from pymcr.mcr import McrAR
mcrar = McrAR()

# MCR assumes a system of the form: D = CS^T
#
# Data that you will provide (hyperspectral context):
# D [n_pixels, n_frequencies]  # Hyperspectral image unraveled in space (2D)
#
# initial_spectra [n_components, n_frequencies]  ## S^T in the literature
# OR
# initial_conc [n_pixels, n_components]   ## C in the literature

# If you have an initial estimate of the spectra
mcrar.fit(D, ST=initial_spectra)

# Otherwise, if you have an initial estimate of the concentrations
mcrar.fit(D, C=initial_conc)
```

Example Results¶

Command line and Jupyter notebook examples are provided in the `Examples/` folder.

From `Examples/Demo.ipynb`:

Citing this Software¶

If you use pyMCR, citing the following article is much appreciated: