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

Dictionary extraction such as c = {**a, **b} not functioning properly. #26

Closed
heetbeet opened this issue Feb 19, 2018 · 5 comments
Closed

Comments

@heetbeet
Copy link

The following was tested on Linux Mint 17, Python version Python 3.6.2 :: Anaconda custom (64-bit) and dotmap version sys.version_info(major=3, minor=6, micro=2, releaselevel='final', serial=0)

  1. (lambda **x:x)(**DotMap(a=1)) returns an unexpected empty dictionary {},
  2. {**DotMap(a=1),**DotMap(b=2)} returns an unexpected empty dictionary {}, and
  3. m = DotMap(); m.a = 2; m.b = 3; print('{a} {b}'.format(**m)); fails with KeyError: 'a'.

Other functionality is working properly such as:

  1. DotMap(a=1)['a'] returns an expected 1, and
  2. DotMap(a=1).a returns an expected 1.
@drgrib
Copy link
Owner

drgrib commented Feb 19, 2018

@heetbeet I'm not able to reproduce item 3, but I can reproduce 1 and 2.

The issue seems to be that, because DotMap inherits from OrderedDict, its own implementations for

  • __len__
  • __iter__
  • __getitem__

are being ignored in these particular types of ** calls and instead being called for the parent OrderedDict class.

I can fix your cases by removing that inheritance and only having it inherit from MutableMapping but that breaks a unit test in __main__ with the title == copy order preservation ==.

If you have immediate suggestions, I'm open to them. Otherwise, I'll have to debug this at a later time.

@heetbeet
Copy link
Author

heetbeet commented Feb 20, 2018

@drgrib I see. I switched over to the following implementation for my dot dictionary needs (I know it clashes for keys that are the same as the dictionary names - such as "pop", "update", "keys", "values", etc.):

class DotDict(dict):
    def __init__(self, **kwds):
        self.update(kwds)
        self.__dict__ = self

So I am not in an immediate need for fixes. I'll switch back to DotMap in the future when doing a bit of code refactoring and the pip default is working nicely again. Thanks for the trouble.

@remcoboerma
Copy link

Shortest test on python2.7.13 for this issue:

>>> dict(**dotmap.DotMap(a=1))
{}

When using ** a lot this means DotMap fails as a dropin replacement for dictionaries. And it would be so nice to have just that.

@drgrib
Copy link
Owner

drgrib commented Nov 12, 2018

I've given this multiple shots and it's honestly too complicated to be worth the trouble when there is a simple workaround available already:

>>> dict(**dotmap.DotMap(a=1).toDict())
{'a': 1}

More on why completely acing the subclass in this manner is so difficult here.

@drgrib drgrib closed this as completed Nov 12, 2018
@drgrib drgrib reopened this Nov 6, 2019
@drgrib
Copy link
Owner

drgrib commented Nov 6, 2019

Fixed in #53

@drgrib drgrib closed this as completed Nov 6, 2019
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

No branches or pull requests

3 participants