Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

DRAFT: DynamicSpec #35

Draft
wants to merge 14 commits into
base: main
Choose a base branch
from
Draft

DRAFT: DynamicSpec #35

wants to merge 14 commits into from

Conversation

sloughran97
Copy link

Code that takes input FITS files and extracts the winds through the Doppler shift of emission spectra. Functionality includes extraction of a single spectrum or an entire image cube, deconvolution of the beam, and the extraction of a zonal wind profile.

Copy link
Owner

@emolter emolter left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi Sarah, just general feedback for now. I do think some re-structuring of various things would be beneficial for the legibility and flexibility of your code - see specific comments. Let me know if you'd like to Zoom about this sometime.

pylanetary/spectral/core.py Outdated Show resolved Hide resolved
centered_list = list(range(-half, half + 1,2))
return centered_list

###############################################################################
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

please remove extraneous comment lines

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will for the final version, but while I'm still developing I find these very helpful to break up reading the code. It's easier for me to understand and read if there are clear delineations between different sections.


###############################################################################

def __init__(self, spec, rest_f, wl = None, freq = None): # stuff that is run when an object is defined
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a stylistic thing, but I am in the habit of minimizing comments like these. This YouTube video explains the philosophy behind this relatively well (the concepts are clear even though I don't know the programming language used in the examples)

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a habit, mainly because I'm not the best at reading other people's code. I'll start moving comments like these to the doc string instead.

pylanetary/spectral/core.py Outdated Show resolved Hide resolved
showplots - indicator of whether to plot or not, string - 'y' or 'Y' will plot the fit results

initial_fit_guess (optional) - path to a saved LMFIT result to use as the initial guess. This can be beneficial if some spectra are very noisy. It is recommended that you use a pixel with as small a Doppler shift as possible to make your initial guess.
RMS (optional) - numerical value of the data's RMS, float
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Functions that return things should also have a Returns section of the docstring.

Generally, for the docstrings, please do your best to make the format identical to the ones in the rest of the code base. Those are based on the Numpy style guide.

pylanetary/spectral/core.py Outdated Show resolved Hide resolved
pylanetary/spectral/core.py Outdated Show resolved Hide resolved
pylanetary/spectral/core.py Outdated Show resolved Hide resolved
pylanetary/spectral/core.py Outdated Show resolved Hide resolved
pylanetary/spectral/core.py Outdated Show resolved Hide resolved
@sloughran97 sloughran97 reopened this Feb 16, 2024

return v, wind_err

model = {}
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

please use a more descriptive variable name. Something like, "lmfit_model_dict"

'''
Input string instantiates object using numpy arrays of the x-axis and the spectral intensity axis.

Parameters
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

docstrings look much better! When I clone this to add dependencies to pyproject.toml, I'll also do my best to fix any residual formatting issues that are causing the readthedocs build to fail

----------
spec : numpy array
The intensity/vertical axis of the spectrum
rest_f : float
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think the rest frequency needs to be in the init of Spectrum; for example, what if you wanted to fit two molecular lines in the same spectrum, or you wanted to test the effect of perturbing the rest frequency a little bit? This could instead be an input parameter to fit_profile.

The intensity/vertical axis of the spectrum
rest_f : float
The rest frequency of molecular transition being examined
x_space : string
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same with this one. I don't think we need to be opinionated about this until the function where lmfit requests it. For example, what if I wanted to try both? I wouldn't want to have to instantiate a new object

Comment on lines +115 to +124
self.wl = wl
self.freq = freq

if self.wl is None and self.freq is None:
raise ValueError('You did not provide an input for the x-axis. Please include a frequency (freq) or wavelength (wl) array.')

if self.wl is None:
self.wl = c/self.freq
elif self.freq is None:
self.freq = c/self.wl
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
self.wl = wl
self.freq = freq
if self.wl is None and self.freq is None:
raise ValueError('You did not provide an input for the x-axis. Please include a frequency (freq) or wavelength (wl) array.')
if self.wl is None:
self.wl = c/self.freq
elif self.freq is None:
self.freq = c/self.wl
if wl is None and freq is None:
raise ValueError('You did not provide an input for the x-axis. Please include a frequency (freq) or wavelength (wl) array.')
if wl is None:
self.wl = c/freq
self.freq = freq
elif freq is None:
freq = c/wl
self.wl = wl

print('Numerical results will be saved in the '+outfile+'.pickle file')
results = {'x':[],'y':[],'center':[],'std':[],'chi':[],'redchi':[]}

for xpix in range (0,self.xpixmax,1):
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why does this happen over self.xpixmax and self.ypixmax, when you have already specified the input data? shouldn't it just be applied to all the data that were requested by this function itself?

The platescale of the data.
body : string
The name of the planetary object you are studying.
cont_label : string
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

probably ok to set a default here

----------
picklefile : string
The path to the pickle file of calculated doppler winds and errors.
platescale : float
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

is this not retrievable from the header?


###############################################################################

def plot_data(self, picklefile, platescale, body, cont_label, title = None, date = None, location = None, spatial = None, variable = None, cmap = None, limits = None, contours = None, hatch = None, savefig = None):
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

hard to evaluate this without seeing the results


###############################################################################

def wind_calc(self, picklefile, restfreq, outfile):
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this function currently does not use self.anything; might be an indication it should exist outside of the Cube object?

@emolter
Copy link
Owner

emolter commented Feb 16, 2024

Nice job Sarah. This is much easier to read code than before. Still quite a few things that could be cleaned up, but great job overall. May I request that you include a Jupyter notebook example with the next draft? Confusingly, this should not go inside the notebooks/ subfolder, but instead inside docs/

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants