Python 类型错误:';功能';缺少一个必需的位置参数:';自我';

Python 类型错误:';功能';缺少一个必需的位置参数:';自我';,python,image,button,tkinter,photoimage,Python,Image,Button,Tkinter,Photoimage,代码: 尝试调用以下3个函数之一时出错: class App: root = Tk() button1 = Button() button2 = Button() button3 = Button() img1 = PhotoImage(file="blueBox.png") img2 = PhotoImage(file="redBox.png") deckImage = PhotoImage(f

代码:

尝试调用以下3个函数之一时出错:

class App:

    root = Tk()
    button1 = Button()
    button2 = Button()
    button3 = Button()

    img1 = PhotoImage(file="blueBox.png")
    img2 = PhotoImage(file="redBox.png")
    deckImage = PhotoImage(file="blackBox.png")
我删除了showcolor1/2/3将调用的函数,因为它们工作正常。使用Buttons命令调用这些函数时出现问题:

    def showcolor1(self):
        if self.card1 != 0:
            self.card2 = 1
        else:
            self.card1 = 1

        self.button1.configure(image=self.getArrayValue(0))
        self.button1.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(0))
以下是全部代码: 它应该显示3个黑色按钮。如果你按下按钮1,它会改变他的颜色。当您按下两个按钮时,它会检查它们是否具有相同的颜色:

    def showcolor2(self):
        if self.card1 != 0:
            self.card2 = 2
        else:
            self.card1 = 2

        self.button2.configure(image=self.getArrayValue(1))
        self.button2.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(1))

    def showcolor3(self):
        if self.card1 != 0:
            self.card2 = 3
        else:
            self.card1 = 3

        self.button2.configure(image=self.getArrayValue(1))
        self.button2.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(2))


    button1 = Button(master=root, text="", image=deckImage, state=NORMAL, command=showcolor1)
    button1.pack()
    button2 = Button(master=root, text="", image=deckImage, state=NORMAL, command=showcolor2)
    button2.pack()
    button3 = Button(master=root, text="", image=deckImage, state=NORMAL, command=showcolor3)
    button3.pack()

    root.mainloop()

a = App()

您没有将参数发送到
showcolor3()
函数

如果要向函数发送参数,可以使用
lambda
函数:

from tkinter import *
class App:
    
    root = Tk()
    testArray = [1, 2, 2]
    cAmount = 0
    card1 = 0
    card2 = 0
    button1 = Button()
    button2 = Button()
    button3 = Button()
    
    img1 = PhotoImage(file="blueBox.png")
    img2 = PhotoImage(file="redBox.png")
    deckImage = PhotoImage(file="blackBox.png")

    def checkCards(self):
        if self.testArray[self.card1] == self.testArray[self.card2]:
            print("CORRECT")
        elif self.testArray[self.card1] != self.testArray[self.card2]:
            print("FALSE")
            if self.card1 == 1 or self.card2 == 1:
                self.button1.configure(image=self.deckImage)
                self.button1.configure(state=NORMAL)
            if self.card1 == 2 or self.card2 == 2:
                self.button2.configure(image=self.deckImage)
                self.button2.configure(state=NORMAL)
            if self.card1 == 3 or self.card2 == 3:
                self.button3.configure(image=self.deckImage)
                self.button3.configure(state=NORMAL)

    def setChoosenPicture(self):
        self.cAmount = self.cAmount + 1
        if self.cAmount == 2:
            self.checkCards()
            self.cAmount = 0
        else:
            return

    def getArrayValue(self, buttonIndex):
        if self.testArray[buttonIndex] == 1:
            return self.img1
        elif self.testArray[buttonIndex] == 2:
            return self.img2

    def showcolor1(self):
        if self.card1 != 0:
            self.card2 = 1
        else:
            self.card1 = 1

        self.button1.configure(image=self.getArrayValue(0))
        self.button1.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(0))

    def showcolor2(self):
        if self.card1 != 0:
            self.card2 = 2
        else:
            self.card1 = 2

        self.button2.configure(image=self.getArrayValue(1))
        self.button2.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(1))

    def showcolor3(self):
        if self.card1 != 0:
            self.card2 = 3
        else:
            self.card1 = 3

        self.button2.configure(image=self.getArrayValue(1))
        self.button2.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(2))


    button1 = Button(master=root, text="", image=deckImage, state=NORMAL, command=showcolor1)
    button1.pack()
    button2 = Button(master=root, text="", image=deckImage, state=NORMAL, command=showcolor2)
    button2.pack()
    button3 = Button(master=root, text="", image=deckImage, state=NORMAL, command=showcolor3)
    button3.pack()

    root.mainloop()


    a = App()

顺便说一下,您似乎还没有在类中定义showcolor函数,但我不能肯定,因为我无法看到整个代码。如果是这种情况,如果要使用实例调用函数,则必须在类中定义该函数


编辑:我看到你编辑了你的问题。您必须先创建一个类,然后为其实例创建方法。您的问题可能是关于OOP的知识不足。查看OOP概念可能是个好主意。

您还没有在类中定义函数。如果存在“self”参数,则必须对实例调用该函数。e、 g如果x是一个实例,那么可以将其称为
x.showcolor3()

代码的问题是,您在
语句中运行了太多内容,而您可能希望稍后在顶层运行它。当您想要使用在类中定义的方法时,这尤其会导致问题。它们使用
self
,它应该引用类的实例。但是您不能在class语句本身的主体内创建实例,因为类尚未完成创建

下面是一个与代码相同的错误示例:

button3 = tk.Button(master=root,text="",command=lambda self = instance: showcolor3(self))
要修复它,您需要将使用方法的代码移出类主体。将它放在函数中可能是有意义的,但如果这更有意义的话,它也可以在顶层工作。在我的简单示例中,它可能会:

class Foo:
    def bar(self):
        print("bar")

    bar()

    # this also won't work, though you won't get here due to the error above
    f = Foo()  # if you remove the line above, this will raise a NameError about Foo
在代码中,您可能希望更多按钮设置代码出现在
\uuuu init\uuu
方法中。在创建每个实例之后,Python将自动调用它。您需要考虑一下,当前正在设计的类变量中,哪些应该由所有实例共享,哪些应该特定于每个实例。我不太了解你对类的设计,因此无法告诉你什么是最好的,尽管创建所有实例属性可能是一个安全的赌注。
\uuuu init\uuu
方法自动获得
self
传递

下面是一个版本的
应用程序
类,它显示了Tkinter程序更典型的样式,所有数据都放在实例变量中,而不是类变量中:

class Foo:
    def bar(self):
        print("bar")

# unindent here!
f = Foo()
f.bar()

请注意,
按钮
对象的初始化变化非常小,它们现在使用的是
命令=self.showcolor1
和类似的方法,而不仅仅是使用方法名。

只需在所有函数中写入最后一行,一切都很完美我运行了它,我遇到了这个错误,请尝试一下

class App:
    # get rid of all the class-variable code
    def __init__(self, root):
        self.root = root
        self.testArray = [1, 2, 2]
        self.cAmount = 0
        self.card1 = 0
        self.card2 = 0
    
        self.img1 = PhotoImage(file="blueBox.png")
        self.img2 = PhotoImage(file="redBox.png")
        self.deckImage = PhotoImage(file="blackBox.png")

        self.button1 = Button(master=root, text="", image=self.deckImage, state=NORMAL, command=self.showcolor1)
        self.button1.pack()
        self.button2 = Button(master=root, text="", image=self.deckImage, state=NORMAL, command=self.showcolor2)
        self.button2.pack()
        self.button3 = Button(master=root, text="", image=self.deckImage, state=NORMAL, command=self.showcolor3)
        self.button3.pack()

    # the rest of the methods are the same


# unindent for some more top level code to start the app running
root = Tk()
app = App(root)
root.mainloop()

老实说,我想我创造了一个类。在第一个代码段上面,它说class App(),在编辑问题时,它只是从代码块滑到文本块中:D或者你是说创建一个类有什么不同吗?我指的是python类。我认为如果共享所有代码会更好,因为似乎没有类,也没有该类的实例。顺便说一句,我不明白类App()是做什么的。你应该编辑你的问题。好的,我编辑了这篇文章,现在所有的代码都可用了。很抱歉,你使用的OOP概念似乎完全错误。我强烈建议您阅读OOP Tkinter示例和OOP概念。建议您阅读教程。我还建议您阅读Python文档。如果您使用的是标准怠速,只需按F1。
image=deckImage
应改为
image=self.deckImage
from tkinter import *


class App:

    root = Tk()
    testArray = [1, 2, 2]
    cAmount = 0
    card1 = 0
    card2 = 0
    button1 = Button()
    button2 = Button()
    button3 = Button()

    img1 = PhotoImage(file="blueBox.png")
    img2 = PhotoImage(file="redBox.png")
    deckImage = PhotoImage(file="blackBox.png")

    def checkCards(self):
        if self.testArray[self.card1] == self.testArray[self.card2]:
            print("CORRECT")
        elif self.testArray[self.card1] != self.testArray[self.card2]:
            print("FALSE")
            if self.card1 == 1 or self.card2 == 1:
                self.button1.configure(image=self.deckImage)
                self.button1.configure(state=NORMAL)
            if self.card1 == 2 or self.card2 == 2:
                self.button2.configure(image=self.deckImage)
                self.button2.configure(state=NORMAL)
            if self.card1 == 3 or self.card2 == 3:
                self.button3.configure(image=self.deckImage)
                self.button3.configure(state=NORMAL)

    def setChoosenPicture(self):
        self.cAmount = self.cAmount + 1
        if self.cAmount == 2:
            self.checkCards()
            self.cAmount = 0
        else:
            return

    def getArrayValue(self, buttonIndex):
        if self.testArray[buttonIndex] == 1:
            return self.img1
        elif self.testArray[buttonIndex] == 2:
            return self.img2

    def showcolor1(self):
        if self.card1 != 0:
            self.card2 = 1
        else:
            self.card1 = 1

        self.button1.configure(image=self.getArrayValue(0))
        self.button1.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(0))

    def showcolor2(self):
        if self.card1 != 0:
            self.card2 = 2
        else:
            self.card1 = 2

        self.button2.configure(image=self.getArrayValue(1))
        self.button2.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(1))

    def showcolor3(self):
        if self.card1 != 0:
            self.card2 = 3
        else:
            self.card1 = 3

        self.button2.configure(image=self.getArrayValue(1))
        self.button2.configure(state=DISABLED)
        self.setChoosenPicture(self.getArrayValue(2))

    button1 = Button(
        master=root, text="", image=deckImage, state=NORMAL, command=showcolor1
    )
    button1.pack()
    button2 = Button(
        master=root, text="", image=deckImage, state=NORMAL, command=showcolor2
    )
    button2.pack()
    button3 = Button(
        master=root, text="", image=deckImage, state=NORMAL, command=showcolor3
    )
    button3.pack()

    root.mainloop()

a = App() //This needs to be out