TypeError: otrzymano wiele wartości argumentu


162

Czytałem inne wątki, które miały związek z tym błędem i wydaje mi się, że mój problem ma interesującą wyraźną różnicę niż wszystkie posty, które przeczytałem do tej pory, a mianowicie wszystkie inne posty do tej pory zawierają błąd dotyczący albo utworzonego przez użytkownika klasa lub wbudowany zasób systemowy. Mam ten problem podczas wywoływania funkcji, nie mogę dowiedzieć się, do czego to może służyć. Jakieś pomysły?

BOX_LENGTH = 100
turtle.speed(0)
fill = 0
for i in range(8):
    fill += 1
    if fill % 2 == 0:
        Horizontol_drawbox(BOX_LENGTH, fillBox = False)
    else:
        Horizontol_drawbox(BOX_LENGTH, fillBox = True)

    for i in range(8):
        fill += 1
        if fill % 2 == 0:
            Vertical_drawbox(BOX_LENGTH,fillBox = False)
        else:
            Vertical_drawbox(BOX_LENGTH,fillBox = True)

Komunikat o błędzie:

    Horizontol_drawbox(BOX_LENGTH, fillBox = True)
TypeError: Horizontol_drawbox() got multiple values for argument 'fillBox'

5
Jaka jest deklaracja Horizontol_drawboxfunkcji? Jeśli zaczyna się od fillBox, to jest to błąd (przypisywany raz argumentem pozycyjnym, a drugi argumentowi słowem kluczowemu).
Cilyan,

Odpowiedzi:


243

Dzieje się tak, gdy określono argument słowa kluczowego, który zastępuje argument pozycyjny. Na przykład wyobraźmy sobie funkcję, która rysuje kolorowe pudełko. Funkcja wybiera kolor, który ma być użyty i deleguje rysowanie ramki do innej funkcji, przekazując wszystkie dodatkowe argumenty.

def color_box(color, *args, **kwargs):
    painter.select_color(color)
    painter.draw_box(*args, **kwargs)

Potem wezwanie

color_box("blellow", color="green", height=20, width=30)

zakończy się niepowodzeniem, ponieważ dwie wartości są przypisane color: "blellow"jako pozycyjna i "green"jako słowo kluczowe. ( painter.draw_boxma zaakceptować argumenty heighti width).

Łatwo to zobaczyć na przykładzie, ale oczywiście jeśli pomieszamy argumenty podczas rozmowy, debugowanie może nie być łatwe:

# misplaced height and width
color_box(20, 30, color="green")

Tutaj colorjest przypisany 20, potem args=[30]i colorponownie przypisany "green".


Ciekawe - kiedy trafiłem na ten błąd, też chodziło o colorkłótnię. Problem był nieco inny - mój model_matrixargument stał się tylko słowem kluczowym, a jakiś starszy kod przekazywał go jako argument pozycyjny. Nowe API oczekiwało colori zamiast tego otrzymało macierz 4x4.
Tomasz Gandor

Cześć, nie rozumiem tego w drugim przykładzie. To również spełnia warunek: When a keyword argument is specified that overwrites a positional argument. Ale dlaczego ten drugi może działać? Jaka jest zasada, gdy Python przypisuje argumenty. Dziękuję Ci.
Alston,

2
@Stallman: drugi podany przeze mnie przykład również nie działa. color = 20 jest w konflikcie z color = „green”. Reguła przypisania jest podana zaraz po. Więcej informacji: docs.python.org/3/tutorial/controlflow.html#keyword-arguments W szczególności trzeci z 4 przykładów „nieprawidłowych wywołań”.
Cilyan

Dostałem ten błąd, gdy robiłam: dict(**{'a': 1}, **{'a': 2}). Działa to dobrze, jeśli nie powtórzyć nazwy param: dict(**{'a': 1}, **{'b': 2}).
Robo Robok

@RoboRobok rzeczywiście, jest to "nowy sposób" (3.5) na uzyskanie błędu i jest opisany w python.org/dev/peps/pep-0448/#specification Sugeruję dodanie własnej odpowiedzi na pytanie, aby to zrobić następnym odwiedzającym łatwiej będzie znaleźć Twoją sugestię.
Cilyan

82

Miałem ten sam problem, który jest naprawdę łatwy do rozwiązania, ale jego przejrzenie zajęło mi trochę czasu.

Skopiowałem deklarację do miejsca, w którym ją stosowałem i zostawiłem tam argument „siebie”, ale uświadomienie sobie tego zajęło mi wieki.

miałem

self.myFunction(self, a, b, c='123')

ale tak powinno być

self.myFunction(a, b, c='123')

1
Lub zastąp najpierw selfnazwą klasy. ;)
Tomasz Gandor

Fantastyczna odpowiedź. To jest dokładnie problem, z którym się spotkałem. Dzięki, Q!
ramhiser

55

Dzieje się tak również, jeśli zapomnisz selfdeklaracji wewnątrz metod klas.

Przykład:

class Example():
    def is_overlapping(x1, x2, y1, y2):
        # Thanks to https://stackoverflow.com/a/12888920/940592
        return max(x1, y1) <= min(x2, y2)

Nie można tego nazwać jak self.is_overlapping(x1=2, x2=4, y1=3, y2=5) z:

{TypeError} is_overlapping () pobrał wiele wartości dla argumentu „x1”

PRACE :

class Example():
    def is_overlapping(self, x1, x2, y1, y2):
        # Thanks to https://stackoverflow.com/a/12888920/940592
        return max(x1, y1) <= min(x2, y2)

1
Ten komentarz pomaga mi dostrzec mój problem: zapomniałem dodać selfargument w deklaracji funkcji. czyli co powinno być def myFunction(self, a, b, c='123')napisane jako def myFunction(a, b, c='123'). A ponieważ bpobiera listę i cprzyjmuje wartość skalarną, gdy brakuje self, argumenty się pomieszały i ostatecznie dane wejściowe btrafiają do c, powodując błąd „wiele argumentów”. Popełniam ten błąd, ponieważ przetestowałem tę wewnętrzną metodę poza klasą i zapomniałem dodać z selfpowrotem. Mam nadzieję, że pomoże to komuś innemu!
yuqli

@yuqli Właśnie w ten sposób również wchodzę w ten problem. ;) Miło słyszeć, że ten post Ci pomógł.
gies0r

1
zaoszczędziło mi też sporo czasu :)
nexla

Działa również po udekorowaniu funkcji, @staticmethodktóra może być lepszym podejściem, gdy selfnie jest z natury wymagana.
ayorgo

25

Mój problem był podobny do Q --- dziesięć, ale w moim przypadku było to, że zapomniałem podać argument własny do funkcji klasy:

class A:
    def fn(a, b, c=True):
        pass

Powinno stać się

class A:
    def fn(self, a, b, c=True):
        pass

Ta wadliwa implementacja jest trudna do zauważenia podczas wywoływania metody klasy jako:

a_obj = A()
a.fn(a_val, b_val, c=False)

Co da TypeError: got multiple values for argument. Miejmy nadzieję, że pozostałe odpowiedzi są wystarczająco jasne, aby każdy mógł szybko zrozumieć i naprawić błąd. Jeśli nie, miej nadzieję, że ta odpowiedź ci pomoże!


3
o
rany

3

Po prostu nie możesz zrobić następujących rzeczy:

class C(object):
    def x(self, y, **kwargs):
        # Which y to use, kwargs or declaration? 
        pass

c = C()
y = "Arbitrary value"
kwargs["y"] = "Arbitrary value"
c.x(y, **kwargs) # FAILS

Ponieważ zmienną „y” przekazujesz do funkcji dwukrotnie: raz jako kwargi i raz jako deklarację funkcji.


2

Przyprowadzono mnie tutaj z powodu, który nie został wyraźnie wymieniony w odpowiedziach do tej pory, aby zaoszczędzić innym kłopotu:

Błąd występuje również wtedy, gdy argumenty funkcji zmieniły kolejność - z tego samego powodu, co w akceptowanej odpowiedzi: argumenty pozycyjne kolidują z argumentami słów kluczowych.

W moim przypadku było tak, ponieważ kolejność argumentów set_axisfunkcji Pandas zmieniła się między 0,20 a 0,22:

0.20: DataFrame.set_axis(axis, labels)
0.22: DataFrame.set_axis(labels, axis=0, inplace=None)

Korzystanie z często spotykanych przykładów set_axis skutkuje tym mylącym błędem, ponieważ gdy dzwonisz:

df.set_axis(['a', 'b', 'c'], axis=1)

przed 0.22, ['a', 'b', 'c']jest przypisany do osi, ponieważ jest to pierwszy argument, a następnie argument pozycyjny dostarcza „wiele wartości”.


1

Ten wyjątek również zostanie zgłoszony za każdym razem, gdy funkcja została wywołana za pomocą kombinacji keyword argumentsi args,kwargs

Przykład:

def function(a, b, c, *args, **kwargs):
    print(f"a: {a}, b: {b}, c: {c}, args: {args}, kwargs: {kwargs}")

function(a=1, b=2, c=3, *(4,))

I wzrośnie:

TypeError                                 Traceback (most recent call last)
<ipython-input-4-1dcb84605fe5> in <module>
----> 1 function(a=1, b=2, c=3, *(4,))

TypeError: function() got multiple values for argument 'a'

A także stanie się to bardziej skomplikowane, gdy użyjesz go niewłaściwie w dziedzictwie . więc uważaj na te rzeczy!

1- Wywołanie funkcji za pomocą keyword argumentsi args:

class A:
    def __init__(self, a, b, *args, **kwargs):
        self.a = a
        self.b = b
    
class B(A):
    def __init__(self, *args, **kwargs):

        a = 1
        b = 2
        super(B, self).__init__(a=a, b=b, *args, **kwargs)

B(3, c=2)

Wyjątek:

TypeError                                 Traceback (most recent call last)
<ipython-input-5-17e0c66a5a95> in <module>
     11         super(B, self).__init__(a=a, b=b, *args, **kwargs)
     12 
---> 13 B(3, c=2)

<ipython-input-5-17e0c66a5a95> in __init__(self, *args, **kwargs)
      9         a = 1
     10         b = 2
---> 11         super(B, self).__init__(a=a, b=b, *args, **kwargs)
     12 
     13 B(3, c=2)

TypeError: __init__() got multiple values for argument 'a'

2- Wywołanie funkcji z keyword argumentsi kwargsktóra zawiera słowa kluczowe argumenty za:

class A:
    def __init__(self, a, b, *args, **kwargs):
        self.a = a
        self.b = b
    
class B(A):
    def __init__(self, *args, **kwargs):

        a = 1
        b = 2
        super(B, self).__init__(a=a, b=b, *args, **kwargs)

B(**{'a': 2})

Wyjątek:

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-7-c465f5581810> in <module>
     11         super(B, self).__init__(a=a, b=b, *args, **kwargs)
     12 
---> 13 B(**{'a': 2})

<ipython-input-7-c465f5581810> in __init__(self, *args, **kwargs)
      9         a = 1
     10         b = 2
---> 11         super(B, self).__init__(a=a, b=b, *args, **kwargs)
     12 
     13 B(**{'a': 2})

TypeError: __init__() got multiple values for keyword argument 'a'
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.