<jupyter_start><jupyter_text>Specutils Analysis![Specutils: An Astropy Package for Spectroscopy](data/specutils_logo.png)This notebook provides an overview of some of the spectral analysis capabilities of the Specutils Astropy coordinated package.  While this notebook is intended as an interactive introduction to specutils at the time of its writing, the canonical source of information for the package is the latest version's documentation: https://specutils.readthedocs.ioNote that the below assumes you have knowledge of the material in the [overview notebook](Specutils_overview.ipynb).  If this is not the case you may wish to review that notebook before proceding here.  ImportsWe start with some fundamental imports for working with specutils and simple visualization of spectra:<jupyter_code>import numpy as np

import astropy.units as u

import specutils
from specutils import Spectrum1D, SpectralRegion
specutils.__version__
# for plotting:
%matplotlib inline
import matplotlib.pyplot as plt


# for showing quantity units on axes automatically:
from astropy.visualization import quantity_support
quantity_support();<jupyter_output><empty_output><jupyter_text>Sample Spectrum and SNRFor use below, we also load the sample SDSS spectrum downloaded in the [overview notebook](Specutils_overview.ipynb).  See that notebook if you have not yet downloaded this spectrum.<jupyter_code>sdss_spec = Spectrum1D.read('data/sdss_spectrum.fits', format='SDSS-III/IV spec')
plt.step(sdss_spec.wavelength, sdss_spec.flux);<jupyter_output><empty_output><jupyter_text>Because this example file already has uncertainties, it is straightforward to use one of the fundamental quantifications of a spectrum: the whole-spectrum signal-to-noise ratio:<jupyter_code>from specutils.analysis import snr

snr(sdss_spec)<jupyter_output><empty_output><jupyter_text>Spectral RegionsMost analysis required on a spectrum requires specification of a part of the spectrum - e.g., a spectral line.  Because such regions may have value independent of a particular spectrum, they are represented as objects distrinct from a given spectrum object.  Below we outline a few ways such regions are specified.<jupyter_code>ha_region = SpectralRegion((6563-50)*u.AA, (6563+50)*u.AA)
ha_region<jupyter_output><empty_output><jupyter_text>Regions can also be raw pixel values (although of course this is more applicable to a specific spectrum):<jupyter_code>pixel_region = SpectralRegion(2100*u.pixel, 2600*u.pixel)
pixel_region<jupyter_output><empty_output><jupyter_text>Additionally, *multiple* regions can be in the same `SpectralRegion` object. This is useful for e.g. measuring multiple spectral features in one call:<jupyter_code>HI_wings_region = SpectralRegion([(1.4*u.GHz, 1.41*u.GHz), (1.43*u.GHz, 1.44*u.GHz)])
HI_wings_region<jupyter_output><empty_output><jupyter_text>While regions are useful for a variety of analysis steps, fundamentally they can be used to extract sub-spectra from larger spectra:<jupyter_code>from specutils.manipulation import extract_region

subspec = extract_region(sdss_spec, pixel_region)
plt.step(subspec.wavelength, subspec.flux)

snr(subspec)<jupyter_output><empty_output>
{'fraction_non_alphanumeric': 0.06792452830188679, 'fraction_numerical': 0.010377358490566037, 'mean_word_length': 6.9525, 'pattern_counts': {'":': 0, '<': 29, '<?xml version=': 0, '>': 29, 'https://': 1, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 2, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'chain_length': '7', 'dir': 'jupyter-structured-clean-dedup', 'id': '168504', 'license': 'BSD-3-Clause', 'n_tokens_mistral': 950, 'n_tokens_neox': 890, 'n_words': 323, 'path': '09b-Specutils/Specutils_analysis.ipynb', 'repo_name': 'eteq/astropy-workshop', 'size': '3180'}