-
Notifications
You must be signed in to change notification settings - Fork 175
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
Allow FrozenObjects to control param init order #1493
Conversation
I think this warrants to revive the discussion whether to have the copy code in a mixin class. |
I don't have a strong opinion one way or the other, but it would be nice to get this resolved quickly as this is breaking NengoDL |
if isinstance(v, Parameter) and not isinstance(v, ObsoleteParam)} | ||
self._paramdict = collections.OrderedDict( | ||
(k, v) for k, v in inspect.getmembers(type(self)) | ||
if isinstance(v, Parameter) and not isinstance(v, ObsoleteParam)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just taking a guess what you're going for here, but keep in mind that inspect.getmembers
returns the members in alphabetical order, not the order they're defined in the code.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, I think that's fine. I just wanted to make them have a consistent order, so that we can rely on some order. Does that make sense?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yeah, can't hurt 👍
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've added a few little fixups. One makes sure the parameters always have a consistent order, just to make things consistent. It also saves a bit of time in __repr__
because we don't have to sort them then.
The other changes are just minor ones for speed: not turning an iterator into a list (since we always just iterate over it), and not having to check if the param is in state
each time through the loop in __setstate__
.
This looks ready to go to me. I don't think we need to hold this up for a discussion about making copying a mixin; that's a discussion that can happen on its own.
Fixups look good to me. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Made an inline comment to explain why something was the way it was. Will change it back in the merge. Aside from that LGTM, merging!
nengo/params.py
Outdated
for p in self._params: | ||
if not p.readonly: | ||
msg = "All parameters of a FrozenObject must be readonly" | ||
raise ReadonlyError(attr=p, obj=self, msg=msg) | ||
|
||
@property | ||
def _params(self): | ||
return list(itervalues(self._paramdict)) | ||
return itervalues(self._paramdict) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So the reason this was a list and not an iterator is because it's a property. When you do thing.attribute
you do not expect to get back an iterator, conventionally iterators are only returned from methods (hence why we have dict.values()
etc rather than dict.values
). This is important because:
param = self._params
for p in param:
# this works fine
for p in param:
# this now fails because the iterator is exhausted
I definitely wouldn't expect this behavior, as an attribute should just give me data. I would be more likely to expect something like this with params = self._iterparams()
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sure, makes sense!
73c879f
to
2904516
Compare
2904516
to
9713a29
Compare
Motivation and context:
With our Parameter validation system, sometimes parameters need to be initialized in a particular order. When copying an object the order is random by default, so we need to impose an order on this. We had this in place for
NengoObjects
, but not forFrozenObjects
. Previously this was fine because we didn't have anyFrozenObjects
where order mattered, but for the newConvolution
object it does matter.I also added a seed for the Convolution test. I had a random test failure at some point that I wasn't able to reproduce again, so I'm not even 100% sure if it was real. But adding a seed here doesn't hurt.
How has this been tested?
Added a new test that fails without this change and passes with it.
How long should this take to review?
Types of changes:
Checklist: