Подавить предупреждение о неожиданном аргументе в миксине - PullRequest
0 голосов
/ 25 мая 2020

Я пишу миксин в Python3 .8:

class Cloneable:
    def change_field(self, **kwargs):
        """ Create a new object with only the specified properties changed."""
        argdict = {**kwargs, **{key: self.__getattribute__(key) for key in self.__slots__ if
                                key not in kwargs and key[:2] != '__'}}
        return self.__class__(**argdict) 

В PyCharm я получаю предупреждение «Неожиданный аргумент» в последней строке. Предположительно это связано с распаковкой аргументов ключевого слова. Если бы это была функция, я мог бы включить **kwargs в сигнатуру функции, но это миксин, и я заранее не знаю, к какому __init__ он будет относиться.

Как я могу подавить такие надоедливые предупреждения?

Ответы [ 2 ]

1 голос
/ 25 мая 2020

Inspect Module

Расширьте ваш миксин с помощью классов, которые его используют, и используйте модуль inspect .

С настройкой ниже мы:

  1. сохраняем список всех имен аргументов из __init__ подкласса
  2. фильтр argdict по нашему списку

Мы подавляем предупреждения, не создавая их.

import inspect

class Mixin:
    @property
    def names(self):
        return self.__names

    def __init__(self):
        sig = inspect.signature(self.__init__)
        self.__names = list()
        for param in sig.parameters.values():             # Signature(a=None, b=None).values()
            self.__names.append(str(param).split('=')[0]) # str(Parameter(a=None)).split('=')[0]
        print(self.names)    # [a, b]

    def change_field(self, **kwargs):
        """ Create a new object with only the specified properties changed."""
        argdict = {**{key: self.__getattribute__(key) for key in self.__slots__}, **kwargs}
        return self.__class__(**{k:v for k, v in argdict.items() if k in self.names})


class App(Mixin):
    def __init__(self, a=None, b=None):
        Mixin.__init__(self)

App()

Подробнее

Вы делали это наоборот. Вы должны позволить kwargs перезаписывать __slots__ ключи. Вы также пытаетесь подавить ключи, заканчивающиеся двойным подчеркиванием. Все, что не принадлежит (включая дандеры), будет удалено в этом последнем фильтре.

0 голосов
/ 26 мая 2020

Мне удалось решить проблему. Спасибо Майклу Guidry за его указание на обратный порядок словарей!

Решение состояло в том, чтобы включить фиктивный метод __init__ в миксин, который принимает **kwargs в качестве аргумента. :

class Cloneable:
    def __init__(self, **kwargs):
        ...

    def change_field(self, **kwargs):
        argdict = {key: self.__getattribute__(key) for key in self.__slots__}
        return self.__class__(**{**argdict, **kwargs})
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...