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

Homogenized Universe #35

Merged
merged 14 commits into from
Nov 14, 2017
Merged

Homogenized Universe #35

merged 14 commits into from
Nov 14, 2017

Conversation

sallustius
Copy link
Contributor

Container for storing and getting data.
Closes #11

Copy link
Collaborator

@drewejohnson drewejohnson left a comment

Choose a reason for hiding this comment

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

Great work @sallustius! 🎆
Two big comments, and a few minor ones

  1. The implementation of the get method needs to be corrected. As the comments indicate, the value of x is not guaranteed to always be the expected value, regardless of the uncertainty given. Secondly, if the uncertainty is True, then the arguments x and dx returned will be identical.

  2. Will need to add some unit tests demonstrating that we can load data correctly, retrieve data correctly, and that errors are raised when things go wrong (i.e. requesting data that does not exist)

  3. Docstrings need a little tweaking to match the numpy style that we are going with.

  4. Some minor cleanliness errors that can likely be fixed by instructing pycharm to reformat the code (Ctrl+Shift+L, I believe). Things like

Yes:  x, y = ('foo', 'bar')
No: x,  y=('foo','bar' )

If you run pycodestyle, the linter should detect these, and ones that you did not cause.



class HomogUniv(_SupportingObject):
"""Class for:
Copy link
Collaborator

Choose a reason for hiding this comment

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

Docstring

Great detailed docstring! 👍 Few comments:

  1. The first line of the docstring should be a brief example of the purpose this object fulfills
  2. Add the parameters for the __init__ method in a Parameters block, labeled with type and description
  3. You don't have to add the methods here, but if you do, they should also have a brief description

Here is a like to the numpy example for classes

Class items

We should probably add a __str__ method here [and in all our objects for that matter] that indicates the following information:

  1. Type of container (class)
  2. Name of the universe
  3. Burnup and step to which this universe corresponds (add units of MWd/kgHM)
  4. If given, the day as well

I add the if given statement, because it's not always guaranteed that the branching reader will have knowledge of the day, as the burnup and step are, by default, included and day is excluded. I think we should add the day argument as optional

Copy link
Contributor Author

@sallustius sallustius Oct 18, 2017

Choose a reason for hiding this comment

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

Done only the first part as discussed

Copy link
Collaborator

Choose a reason for hiding this comment

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

The __str__ issue will be addressed in the process of closing #36

"""

def __init__(self, container, name, bu, step, day):
""" Class Initializer. Each universe is defined uniquely
Copy link
Collaborator

Choose a reason for hiding this comment

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

Typically, private methods don't need docstrings, unless they are super confusing. The required input parameters can be listed in the class docstring above, of the manner

Parameters
------------
x: type
    <description on x>
y: str or list or None or whatever
    <description on y>

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

self.infUnc = {}

def set(self, variablename, variablevalue, uncertainty=False):
"""
Copy link
Collaborator

Choose a reason for hiding this comment

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

For multiline docstrings, practice is to leave the first line empty, and add a single line declarative statement describing the method/object. Further sections can be added below.
See above comment for documenting parameters.

Maybe include a Raises section in the docstring indicating that a warning message is raised if a variable is overwritten 🤷‍♂️

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

# 1. Check the input type
variablename = _SupportingObject._convertVariableName(variablename)
if not isinstance(uncertainty, bool):
raise messages.error("Uncertainty must be a boolean variable")
Copy link
Collaborator

Choose a reason for hiding this comment

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

Great! Add an indication of what type of variable was passed in to this method to make the error more helpful

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

setter[variablename] = variablevalue

def get(self, variablename, uncertainty=False):

Copy link
Collaborator

Choose a reason for hiding this comment

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

Add a docstring. This should include a Returns section indicating the data types of variables to be returned

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

if not uncertainty:
return x
else:
dx = setter.get(variablename)
Copy link
Collaborator

Choose a reason for hiding this comment

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

Here, x and dx will be the same item, as both are taken from the same setter dictionary. Will need to grab the appropriate uncertainty dictionary as well

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

# 2. Pointer to the proper dictionary
setter = self._lookup(variablename, uncertainty)
# 3. Return the value of the variable
x = setter.get(variablename)
Copy link
Collaborator

Choose a reason for hiding this comment

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

This does not ensure that x is always the expected value. If uncertainty is True, then x will actually be what dx should be. We need to guaruntee that, regardless of the value of uncertainty, x is the expected value from the correct inf/b1 dictionary.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

dx = setter.get(variablename)
return x, dx

def _lookup(self,variablename, uncertainty):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Single space after items in lists/tuples/functions/etc e.g.
_lookup(self, variableName, uncertainty):
Mixed case variables as well

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

else:
return self.b1Unc

messages.error('Neither inf, nor b1 in the string')
Copy link
Collaborator

Choose a reason for hiding this comment

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

Two items here.

  • Like the above error with the bad uncertainty type, the name of the variable should be passed into this error. This way, the user knows what our program is interpreting.
  • Last line in the file should be blank

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

@@ -0,0 +1,92 @@
import numpy
Copy link
Collaborator

Choose a reason for hiding this comment

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

The numpy module isn't used here, so this line can be removed.

Further, could you add a brief module level docstring at the top of this file? It largely just needs to indicate the purpose of the file and classes present (to be expanded as we go)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

@drewejohnson drewejohnson added this to the Version 1.0.0 milestone Oct 17, 2017
@drewejohnson drewejohnson self-assigned this Oct 17, 2017
Copy link
Collaborator

@drewejohnson drewejohnson left a comment

Choose a reason for hiding this comment

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

Thank you for addressing the previous comments. I added a few small things relating to our previous conversations about storing non-xs related data (group structure, for example) on the object.

Unit tests are still required, but this file is nearly complete

results reader to store data for a single homogenized universe at a single
instance in time.
"""

from serpentTools.objects import _SupportingObject
Copy link
Collaborator

Choose a reason for hiding this comment

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

From #40, there is no longer a preceeding _ in the SupportingObject class

""" Class Initializer. Each universe is defined uniquely
in terms of the attributes mentioned in the docstring. The input
container refers to the name of the parser (branching/results reader).
"""
_SupportingObject.__init__(self, container)
Copy link
Collaborator

Choose a reason for hiding this comment

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

Actually, since we have a name, use the NamedObject, and pass the name and the container into the __init__ here. Removes the need to also write self.name = name 😜

# 3. Check if variable is already present. Then set the variable.
if variablename in setter:
if variableName in setter:
messages.warning('The variable will be overwritten')
Copy link
Collaborator

Choose a reason for hiding this comment

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

Add the name of the variable to this line

# 1. Check the input values
variablename = _SupportingObject._convertVariableName(variablename)
variableName = _SupportingObject._convertVariableName(variableName)
Copy link
Collaborator

Choose a reason for hiding this comment

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

Please remove.
This is only necessary if the variable name requested is SERPENT_STYLE. We will make it known to the user that the variables are stored with mixedCase names.

if not uncertainty:
return self.b1Exp
else:
return self.b1Unc

messages.error('Neither inf, nor b1 in the string')
messages.error('%s not found.The string must contain either the ...'
'inf, or b1 substring.', variableName)
Copy link
Collaborator

Choose a reason for hiding this comment

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

Option to add other data like group structure to the object?

@gridley
Copy link
Contributor

gridley commented Nov 8, 2017

Python doesn't have any private data, so why are you guys using setters and getters?

Copy link
Collaborator

@drewejohnson drewejohnson left a comment

Choose a reason for hiding this comment

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

Nearly done! Some changes to the errors calls (using TypeErrors vs. messages.error) and renaming the test methods to indicate what they are testing

"""
# 1. Check the input values
if not isinstance(uncertainty, bool):
raise messages.error('The variable uncertainty has type %s.\n ...'
Copy link
Collaborator

Choose a reason for hiding this comment

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

Have this raise a TypeError with the same message instead. Same with the call in the addData method

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

@@ -11,7 +11,7 @@


class BranchTester(unittest.TestCase):
"""Classs for testing the branching coefficient file reader."""
"""Class for testing the branching coefficient file reader."""
Copy link
Collaborator

Choose a reason for hiding this comment

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

👍

from serpentTools.parsers import DepletionReader


class containerTester(unittest.TestCase):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Change the name of this class to reflect the container being tested. We have/will have many containers down the road

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done. Changed in "HomogenizedUniverseTester"


@classmethod
def setUpClass(cls):
container = DepletionReader(None)
Copy link
Collaborator

Choose a reason for hiding this comment

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

Pedantic/non-crucial request: Can you just pass DepletionReader(None) as the first argument to containers.HomogUniv? There isn't a need to store the Depletion reader after the creation of the HomogUniv

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

for kk in cls.Unc:
cls.univ.addData(kk, cls.Unc[kk], True)

def test_1(self):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Rename the test to indicate the purpose of this test, i.e. test_getB1Exp

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

d[kk] = self.univ.get(kk,False)
self.assertDictEqual(self.b1Exp,d)

def test_2(self):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Same as ⬆️

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

d[kk] = self.univ.get(kk,True)
self.assertDictEqual(self.b1Unc,d)

def test_3(self):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Same as ⬆️

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

d[kk] = self.univ.get(kk, False)
self.assertDictEqual(self.infExp, d)

def test_4(self):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Same as ⬆️

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

d[kk] = self.univ.get(kk, True)
self.assertDictEqual(self.infUnc, d)

def test_5(self):
Copy link
Collaborator

Choose a reason for hiding this comment

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

Same as ⬆️

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

Copy link
Collaborator

@drewejohnson drewejohnson left a comment

Choose a reason for hiding this comment

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

🎉 🎆 🎉 :octocat: ✔️

@drewejohnson drewejohnson merged commit 06b5e92 into develop Nov 14, 2017
drewejohnson pushed a commit that referenced this pull request Dec 4, 2017
Incorporated changes from PR #35 so that the variables are stored in the homogenized universe containers.

Since the variables requested in reader.settings['variables'] may or may not exactly appear in the SERPENT output, a handy method _checkAddVariable was added to XSReader class. This will perform the following checks to see if a variable should be stored: No variables requested -> True; variable directly appears in requested variables -> True; User has requested that B1XS be stored and variable appears without B1_ -> True; User has requested that infinite xs be stored and variable appears without INF_ -> True; Otherwise, return False.

This check is needed because we don't store ALL of the variable names in our settings dictionary, because there are a lot of double counts (INF_TOT and B1_TOT)

Also added testing for the branching reader

Signed-off-by: Andrew Johnson <1drew.e.johnson@gmail.com>
drewejohnson added a commit that referenced this pull request Dec 13, 2017
* Updated gitignore to exclude pycharm project settings
* Skeleton files for each reader class; Basic directory setup
* Depletion reader and project settings (#1)
* Quick: DepletedMaterial returns time vector if not given as input (#2)
* Quick fix: DepletedMaterial getXY only returns time if no time is given as input
* Fixes #3; Cleaned up reader subclasses (#4)
* Fixes #3; Cleaned up reader subclasses
* Added versioneer (#18)
* Fix get xy (#21)
* Fixes #19: Material doesn't return days if given as input
* Fixed unit tests
* Versioneer (#23)
* Messages, logging, and exception (#24)
* Expand variable groups; XSReader base; Temporary settings  (#27)
* Branching testing; Temporary settings modification
* Initial documentation - sphinx (#28)
* Added variables.yaml to data_files in setup (#32)
* Added depreciation and future warning decorators; More debug statements (#34)
* Depletion reader now correctly adds data from TOT; Updated defaults (#39)
* Better support (#40)
* Added python 2.7 support (#41)
* Homogenized Universe (#35)
* Read depmtx (#44)
* Return A matrix from depmtx as csc matrix not csr (#46)
* Remove settings package; Cleaned up messages file (#47)
* Implemented a module level read function (#48)
* Examples (#49)
* depmtx reader now parses using regular expressions (#52)
* Updated documentation - developer guide, api, and examples (#59)
* Updated setup.py to begrudgingly support distutils (#61)
* Use warnings.catch_warnings to record warnings in test_settings (#55)
* Native drewtils (#62)
* Branching Reader (#65)
* Release 0.1.0
drewejohnson added a commit that referenced this pull request Dec 13, 2017
* Release 0.1.0 (#66)

* Updated gitignore to exclude pycharm project settings
* Skeleton files for each reader class; Basic directory setup
* Depletion reader and project settings (#1)
* Quick: DepletedMaterial returns time vector if not given as input (#2)
* Quick fix: DepletedMaterial getXY only returns time if no time is given as input
* Fixes #3; Cleaned up reader subclasses (#4)
* Fixes #3; Cleaned up reader subclasses
* Added versioneer (#18)
* Fix get xy (#21)
* Fixes #19: Material doesn't return days if given as input
* Fixed unit tests
* Versioneer (#23)
* Messages, logging, and exception (#24)
* Expand variable groups; XSReader base; Temporary settings  (#27)
* Branching testing; Temporary settings modification
* Initial documentation - sphinx (#28)
* Added variables.yaml to data_files in setup (#32)
* Added depreciation and future warning decorators; More debug statements (#34)
* Depletion reader now correctly adds data from TOT; Updated defaults (#39)
* Better support (#40)
* Added python 2.7 support (#41)
* Homogenized Universe (#35)
* Read depmtx (#44)
* Return A matrix from depmtx as csc matrix not csr (#46)
* Remove settings package; Cleaned up messages file (#47)
* Implemented a module level read function (#48)
* Examples (#49)
* depmtx reader now parses using regular expressions (#52)
* Updated documentation - developer guide, api, and examples (#59)
* Updated setup.py to begrudgingly support distutils (#61)
* Use warnings.catch_warnings to record warnings in test_settings (#55)
* Native drewtils (#62)
* Branching Reader (#65)
* Release 0.1.0
@drewejohnson drewejohnson deleted the homog_universe_ste branch February 23, 2018 13:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants