diff --git a/README.md b/README.md index 87c24d67..f06a9d31 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ [**Detailed documentation: https://rpoleski.github.io/MulensModel/**](https://rpoleski.github.io/MulensModel/) -[Latest release: 2.10.1](https://github.com/rpoleski/MulensModel/releases/latest) and we're working on further developing the code. +[Latest release: 2.11.0](https://github.com/rpoleski/MulensModel/releases/latest) and we're working on further developing the code. MulensModel can generate a microlensing light curve for a given set of microlensing parameters, fit that light curve to some data, and return a chi2 value. That chi2 can then be input into an arbitrary likelihood function to find the best-fit parameters. @@ -56,5 +56,5 @@ If you want to contribute to MulensModel, then please see [this file](CONTRIBUTI [![Poleski & Yee 2019](https://img.shields.io/badge/ADS-Poleski%20%26%20Yee%202019-brightgreen.svg)](https://ui.adsabs.harvard.edu/abs/2019A%26C....26...35P/abstract) [![astro-ph/1803.01003](https://img.shields.io/badge/astro--ph-1803.01003-brightgreen.svg)](https://arxiv.org/abs/1803.01003) -file revised Jul 2022 +file revised Oct 2022 diff --git a/documents/MM_v3.md b/documents/MM_v3.md index c4588404..cfebcacf 100644 --- a/documents/MM_v3.md +++ b/documents/MM_v3.md @@ -15,9 +15,10 @@ Once the changes are accepted to be made, **mark them in the code using warnings * `ModelParameters.is_static` -> `is_lens_static` * ephemerides\_file -> ephemeris\_file - maybe * Model.get\_residuals should have keyword phot\_fmt, not type to be consistent with other functions + * test\_MulensData.py - in test\_copy() remove warnings.catch\_warnings() because you remove coords, ra, and dec from init ### Yet unsorted/undecided: - * `Model.set_times()` - `n_epochs` should be None as default, so that we can check if both dt and `n_epochs` were set + * `Model.set\_times()` - `n\_epochs` should be None as default, so that we can check if both dt and `n\_epochs` were set * Caustics.get\_caustics() should return np.arrays, not lists * check all NotImplementedError and maybe remove some functions/options * somehow change which\_parameters() in modelparameters.py - maybe remove diff --git a/source/MulensModel/mulensdata.py b/source/MulensModel/mulensdata.py index e1d4940c..15220fcc 100644 --- a/source/MulensModel/mulensdata.py +++ b/source/MulensModel/mulensdata.py @@ -134,7 +134,7 @@ def __init__(self, data_list=None, file_name=None, if plot_properties is None: plot_properties = dict() - self.plot_properties = plot_properties + self._plot_properties = plot_properties self._import_photometry(data_list, **kwargs) @@ -290,6 +290,24 @@ def _set_coords(self, coords=None, ra=None, dec=None): if ra is not None: raise AttributeError(coords_msg) + @property + def plot_properties(self): + """ + *dict* + + Settings that specify how the photometry should be plotted. + + The keys in this *dict* could be either special keys introduced here + (i.e., ``show_bad`` and ``show_errorbars``) or keys accepted by + matplotlib.pyplot plotting functions. The latter could be for example + ``color``, ``marker``, ``label``, ``alpha``, ``zorder``, + ``markersize``, or ``visible``. + + See :py:class:`~MulensModel.mulensdata.MulensData` + for more information. + """ + return self._plot_properties + def plot(self, phot_fmt=None, show_errorbars=None, show_bad=None, subtract_2450000=False, subtract_2460000=False, model=None, plot_residuals=False, **kwargs): @@ -754,3 +772,27 @@ def ephemerides_file(self): File with satellite ephemeris. """ return self._ephemerides_file + + def copy(self): + """ + Returns a copy of given instance with settings copied + + Returns : + mulens_data: :py:class:`~MulensModel.mulensdata.MulensData` + Copy of self. + """ + data_and_err = self.data_and_err_in_input_fmt() + kwargs = { + 'data_list': [self.time, *list(data_and_err)], + 'phot_fmt': self.input_fmt, 'chi2_fmt': self._chi2_fmt, + 'coords': self.coords, 'ephemerides_file': self._ephemerides_file, + 'add_2450000': self._init_keys['add245'], + 'add_2460000': self._init_keys['add246'], + 'bandpass': self.bandpass, 'bad': np.array(self.bad), + 'plot_properties': {**self.plot_properties} + } + + out = MulensData(**kwargs) + out._file_name = self._file_name + + return out diff --git a/source/MulensModel/tests/test_MulensData.py b/source/MulensModel/tests/test_MulensData.py index 8aa793bf..8a197af1 100644 --- a/source/MulensModel/tests/test_MulensData.py +++ b/source/MulensModel/tests/test_MulensData.py @@ -1,6 +1,7 @@ import os import unittest import numpy as np +import warnings import MulensModel as mm @@ -37,11 +38,49 @@ def test_wrong_length(self): t = np.array([7500., 7501.]) m = np.array([21.0, 21.1]) e_long = np.array([0.001, 1.000, 0.1]) - data = mm.MulensData(data_list=[t, m, e_long]) + _ = mm.MulensData(data_list=[t, m, e_long]) def test_wrong_type(self): with self.assertRaises(TypeError): t = np.array([2457500., 2457501.], dtype=np.float32) m = np.array([21.0, 21.1]) e = np.array([0.001, 1.000]) - data = mm.MulensData(data_list=[t, m, e]) + _ = mm.MulensData(data_list=[t, m, e]) + + +def test_copy(): + """ + Test copying method + """ + n_epochs = len(np.loadtxt(SAMPLE_FILE_01)) + random_bool = np.random.choice([False, True], n_epochs, p=[0.1, 0.9]) + + with warnings.catch_warnings(): + warnings.simplefilter("ignore", category=FutureWarning) + data_1 = mm.MulensData(file_name=SAMPLE_FILE_01, ra="18:00:00", + dec="-30:00:00", good=random_bool) + data_2 = data_1.copy() + + data = [data_1.time, 100.+0.*data_1.time, 1.+0.*data_1.time] + data_3 = mm.MulensData(data, phot_fmt='flux', bad=random_bool) + data_4 = data_3.copy() + + assert isinstance(data_2, mm.MulensData) + assert isinstance(data_4, mm.MulensData) + + attributes = ['time', 'mag', 'err_mag', 'flux', 'err_flux', + 'bad', 'good', 'plot_properties'] + for attribute in attributes: + value_1 = getattr(data_1, attribute) + value_2 = getattr(data_2, attribute) + assert value_1 is not value_2 + assert np.all(value_1 == value_2) + value_1 = getattr(data_3, attribute) + value_2 = getattr(data_4, attribute) + assert value_1 is not value_2 + assert np.all(value_1 == value_2) + + assert data_1.coords == data_2.coords + assert data_1.coords is not data_2.coords + assert data_3.coords is None + assert data_4.coords is None diff --git a/source/MulensModel/version.py b/source/MulensModel/version.py index d0e4243a..7f6646a7 100644 --- a/source/MulensModel/version.py +++ b/source/MulensModel/version.py @@ -1 +1 @@ -__version__ = "2.10.10" +__version__ = "2.11.0"