Skip to content

No overload variant of "fromkeys" of "dict" matches argument types [typing.Iterable[Any], Union[Any, def (*Any, **Any) -> Any]] #2254

Closed

Description

@trnsnt

Hello,

I have defined a dict wrapper where I override fromkeys method.
I have this method signature

    def fromkeys(cls, iterable, value=None):
        # type: (Iterable, Union[Any, Callable]) -> DictWrapper

and this give me the following error : No overload variant of "fromkeys" of "dict" matches argument types [typing.Iterable[Any], Union[Any, def (_Any, *_Any) -> Any]]

Thanks !

Activity

  1. gvanrossum commented on Oct 14, 2016

    @gvanrossum
    Member

    Thanks for the question! I'd be happy to help but I'm not sure I understand the context of that definition. Can you show a complete, small, self-contained program that exhibits this behavior?

  2. trnsnt commented on Oct 14, 2016

    @trnsnt
    Author

    Hello, thanks for the reply. Here is what I have done.
    I have this class

    class DictWrapper(dict):
    
        @classmethod
        def fromkeys(cls, iterable, value=None):
            # type: (Iterable, Union[Any, Callable]) -> DictWrapper
            if not callable(value):
                return DictWrapper(super(d, cls).fromkeys(iterable, value))
    
            def _():
                for key in iterable:
                    yield key, value(key)
    
            return DictWrapper(_())
    

    Code is working fine (Python 3.5), but when I run mypy, I have the following error :

    No overload variant of "fromkeys" of "dict" matches argument types [typing.Iterable[Any], Union[Any, def (Any, *Any) -> Any]]
    

    I am not sure if it is a problem, or if I have done something wrong.

  3. gvanrossum commented on Oct 14, 2016

    @gvanrossum
    Member

    Oh, it seems you've hit two issues! When I run that example I get:

    __tmp__.py: note: In class "DictWrapper":
    __tmp__.py:6: error: Signature of "fromkeys" incompatible with supertype "dict"
    __tmp__.py: note: In member "fromkeys" of class "DictWrapper":
    __tmp__.py:9: error: No overload variant of "fromkeys" of "dict" matches argument types [typing.Iterable[Any], Union[Any, def (*Any, **Any) -> Any]]
    

    (Line 6 is the def, line 9 is the super() call.)

    The first complaint is because in typeshed, fromkeys() is defined as a static method, while it is actually a class method. I don't know why this is, but I think I can just fix that.

    The second complaint is probably because mypy doesn't understand callable(value) and hence it doesn't believe that the value you pass to the superclass version of fromkeys() matches the required type. This is issue #1973.

    My recommendation is to add a # type: ignore to the offending line and proceed.

  4. rwbarton commented on Oct 14, 2016

    @rwbarton
    Contributor

    Isn't the second error just because you passed an Iterable, but dict.fromkeys expects a Sequence?

  5. gvanrossum commented on Oct 14, 2016

    @gvanrossum
    Member

    Oh, good catch! I will fix that at the same time. Wait for the next iteration of python/typeshed#604.

  6. gvanrossum commented on Oct 14, 2016

    @gvanrossum
    Member

    OK then I think I have fixed both issues and this can be closed. @trnsnt, to get the fix right away you'll have to pull down the mypy repo, git submodule update, and then in the typeshed subdir do something like "git co master; git pull".

  7. gvanrossum commented on Oct 15, 2016

    @gvanrossum
    Member

    Sadly making fromkeys() a classmethod breaks, due to #328, so this is not fixed. Really sorry!! I went too fast here.

  8. gvanrossum commented on Oct 15, 2016

    @gvanrossum
    Member

    (And this is not a duplicate of that issue -- there's the separate problem that Reid pointed out about the real fromkeys() taking an Iterable.)

  9. added
    bugmypy got something wrong
    and removed on Oct 15, 2016
  10. gvanrossum commented on Oct 20, 2016

    @gvanrossum
    Member

    Keeping this open until #328 is fixed and typeshed has been updated.

  11. added this to the milestone on Oct 27, 2016
  12. removed this from the milestone on Mar 29, 2017
  13. JelleZijlstra commented on Mar 19, 2022

    @JelleZijlstra
    Member

    Seems like this is fixed. This variation of the OP's post:

    from typing import *
    
    class DictWrapper(dict):
    
        @classmethod
        def fromkeys(cls, iterable, value=None):
            # type: (Iterable, Union[Any, Callable]) -> DictWrapper
            if not callable(value):
                return DictWrapper(super(DictWrapper, cls).fromkeys(iterable, value))
    
            def _():
                for key in iterable:
                    yield key, value(key)
    
            return DictWrapper(_())
    

    produces no errors on current mypy

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions