Source code for feets.extractors.ext_structure_functions
#!/usr/bin/env python
# -*- coding: utf-8 -*-
# Copyright (c) 2017-2024, Cabral, Juan
# Copyright (c) 2025, QuatroPe; ClariĆ”, Felipe
# License: MIT
# Full Text:
# https://github.com/quatrope/feets/blob/master/LICENSE
# =============================================================================
# DOC
# =============================================================================
"""Structure functions extractor."""
# =============================================================================
# IMPORTS
# =============================================================================
import numpy as np
from scipy.interpolate import interp1d
from .extractor import Extractor, feature_warning
from ..libs import doctools
# =============================================================================
# EXTRACTOR CLASS
# =============================================================================
[docs]
class StructureFunctions(Extractor):
r"""TStructure functions extractor.
The structure function of rotation measures (RMs) contains information
on electron density and magnetic field fluctuations.
References
----------
.. [simonetti1984small] Simonetti, J. H., Cordes, J. M., & Spangler, S. R.
(1984). Small-scale variations in the galactic magnetic field-The
rotation measure structure function and birefringence in interstellar
scintillations. The Astrophysical Journal, 284, 126-134.
Examples
--------
>>> fs = feets.FeatureSpace(only=[
... 'StructureFunction_index_21',
... 'StructureFunction_index_31',
... 'StructureFunction_index_32',
... ])
>>> features = fs.extract(**lc_normal)
>>> features[0]
{'StructureFunction_index_21': np.float64(1.6029987396657115),
'StructureFunction_index_31': np.float64(2.050072565193364),
'StructureFunction_index_32': np.float64(1.4137753817054497)}
"""
features = [
"StructureFunction_index_21",
"StructureFunction_index_31",
"StructureFunction_index_32",
]
[docs]
@doctools.doc_inherit(Extractor.extract)
def extract(self, magnitude, time):
"""
Parameters
----------
magnitude : array-like
time : array-like
"""
Nsf, Np = 100, 100
sf1, sf2, sf3 = np.zeros(Nsf), np.zeros(Nsf), np.zeros(Nsf)
f = interp1d(time, magnitude)
time_int = np.linspace(np.min(time), np.max(time), Np)
mag_int = f(time_int)
for tau in np.arange(1, Nsf):
sf1[tau - 1] = np.mean(
np.power(np.abs(mag_int[: Np - tau] - mag_int[tau:Np]), 1.0)
)
sf2[tau - 1] = np.mean(
np.abs(
np.power(
np.abs(mag_int[: Np - tau] - mag_int[tau:Np]), 2.0
)
)
)
sf3[tau - 1] = np.mean(
np.abs(
np.power(
np.abs(mag_int[: Np - tau] - mag_int[tau:Np]), 3.0
)
)
)
sf1_log = np.log10(np.trim_zeros(sf1))
sf2_log = np.log10(np.trim_zeros(sf2))
sf3_log = np.log10(np.trim_zeros(sf3))
if len(sf1_log) and len(sf2_log):
m_21, b_21 = np.polyfit(sf1_log, sf2_log, 1)
else:
feature_warning("Can't compute StructureFunction_index_21")
m_21 = np.nan
if len(sf1_log) and len(sf3_log):
m_31, b_31 = np.polyfit(sf1_log, sf3_log, 1)
else:
feature_warning("Can't compute StructureFunction_index_31")
m_31 = np.nan
if len(sf2_log) and len(sf3_log):
m_32, b_32 = np.polyfit(sf2_log, sf3_log, 1)
else:
feature_warning("Can't compute StructureFunction_index_32")
m_32 = np.nan
return {
"StructureFunction_index_21": m_21,
"StructureFunction_index_31": m_31,
"StructureFunction_index_32": m_32,
}