Как исправить tkinter TypeError: ключи должны быть str, int, float, bool или None, а не Button? - PullRequest
0 голосов
/ 04 апреля 2020
import json 
from tkinter import *
import os

listai = json.load(open("listai.txt"))
listap = json.load(open("listap.txt"))
dict = {}



def dictAdd(item, value):
     global listai, listap
     print(item) #i did this so i could see where it was getting the error
     print(value)
     if item not in listai:
          dictcreator()
          d = open("dicionario.txt", "w")
          dict[item] = value
          d.write(json.dumps(dict))
          listai.append(item)
          try:
               listap.append(float(value))
          except ValueError:
               listap.append(int(value))
          i = open("listai.txt", "w").write(json.dumps(listai))
          p = open("listap.txt", "w").write(json.dumps(listap))

#dictAdd("cereja", 3.9)



def dictcreator():
     global listai, listap
     for x in range(len(listai)):
          dict[listai[x]] = listap[x]
     d = open("dicionario.txt", "w").write(json.dumps(dict))

#dictcreator()


def Add():
     addtop = Toplevel()
     addtopheight = 300
     addtopwidth = 300
     addentryname = StringVar()
     addentryprice = StringVar()
     xwpos = int(mainwindow.winfo_screenwidth()/2 - addtopwidth/2)
     ywpos = int(mainwindow.winfo_screenheight()/2 - addtopheight/2)
     addtop.geometry(f"{addtopwidth}x{addtopwidth}+{xwpos}+{ywpos}")
     addtop.resizable(height = 0, width = 0)
     addtop.config(bg="lightgrey")
     addmainlabel = Label(addtop, text="Adicionar alimento novo", font="arial, 19", fg="green", bg="lightgrey").grid(pady=10, padx=8, row=0, column=0, columnspan=2)
     addlabeln = Label(addtop, text="Alimento -->", bg="lightgrey", font="arial, 10").grid(row=1, column=0, padx=2, pady=8)
     addentryn = Entry(addtop, bg="lightgrey", textvariable = addentryname).grid(row=1, column=1, padx=2, pady=5)
     addlabelp = Label(addtop, text="Preço-->", bg="lightgrey", font="arial, 10").grid(row=2, column=0, padx=2, pady=8)
     addentryp = Entry(addtop, bg="lightgrey", textvariable = addentryprice).grid(row=2, column=1, padx=2, pady=5)
     addbutton = Button(addtop, text="Adicionar", font="arial, 10", fg="green", relief=GROOVE, bg="lightgrey", command = lambda: dictAdd(str(addentryname.get()), str(addentryprice.get())))
     addbutton.grid(pady= 20, padx=10, row=3, column=0, columnspan=2)
     addtop.mainloop()
def mainwindow():
     global mainwindow
     width = 700
     height = 400
     mainwindow = Tk()
     xwpos = int(mainwindow.winfo_screenwidth()/2 - width/2)
     ywpos = int(mainwindow.winfo_screenheight()/2 - height/2)
     mainwindow.geometry(f"{width}x{height}+{xwpos}+{ywpos}")
     mainwindow.config(bg="lightgrey")
     mainwindow.title("Lista de Compras")
     mainwindow.resizable(height = 0, width = 0)

     mainlabel = Label(mainwindow, text="Lista de Compras", fg="grey", width=18, bg="lightgrey", font="arial, 32", justify="right").grid(pady=15, padx = 10, row=0, column=0, columnspan = 4)
     Button(mainwindow, text="Add", fg="green", width=5, command=Add, relief=GROOVE).grid(padx= 20, pady=2, row=0, column=5)

     def edit():
          edittop = Toplevel()
          edittopheight = 200
          edittopwidth = 200
          xwpos = int(mainwindow.winfo_screenwidth()/2 - edittopwidth/2)
          ywpos = int(mainwindow.winfo_screenheight()/2 - edittopheight/2)
          edittop.geometry(f"{edittopwidth}x{edittopwidth}+{xwpos}+{ywpos}")
          Label(edittop, text="w").grid(row=0, column=0)
          edittop.mainloop


     for x in range(1, len(listai) + 1):
          listai[x-1] = Label(mainwindow, text=f"{listai[x-1]} --> {listap[x-1]}€", font="18", fg="black", bg="lightgrey", justify="left", width=15).grid(padx = 10, pady = 2, row=x, column=1)
          listai[x-1] = Entry(mainwindow, fg="black", bg="lightgrey", textvariable=f"{listai[x-1]}tv").grid(padx = 5, pady=2, row=x, column=2)
          listai[x-1] = Button(mainwindow, text="Edit", fg="purple", width=5, command=edit, relief=GROOVE).grid(padx= 20, pady=2, row=x, column=4)
          listai[x-1] = Button(mainwindow, text="Eliminate", fg="red", width=7, command=edit, relief=GROOVE).grid(padx= 20, pady=2, row=x, column=5)

          listai[x-1] = Button(mainwindow, text="Eliminate", fg="red", width=7, command=edit, relief=GROOVE)#.grid(padx= 20, pady=2, row=x, column=5)
          listai[x-1] = Button(mainwindow, text="Eliminate", fg="red", width=7, command=edit, relief=GROOVE)#.grid(padx= 20, pady=2, row=x, column=5)


     mainwindow.mainloop()

mainwindow()

Я получаю сообщение об ошибке: «TypeError: ключи должны быть str, int, float, bool или None, а не Button», когда я нажимаю кнопку «addbutton». При необходимости, здесь немного больше вывода терминал:

laranja
5.7
Exception in Tkinter callback
Traceback (most recent call last):
  File "C:\Users\Asus\AppData\Local\Programs\Python\Python38-32\lib\tkinter\__init__.py", line 1883, in __call__
return self.func(*args)
  File "c:/Users/Asus/PycharmProjects/lista de compras/lista de compras.py", line 57, in <lambda>
addbutton = Button(addtop, text="Adicionar", font="arial, 10", fg="green", relief=GROOVE, bg="lightgrey", command = lambda: dictAdd(str(addentryname.get()), str(addentryprice.get())))
  File "c:/Users/Asus/PycharmProjects/lista de compras/lista de compras.py", line 16, in dictAdd
dictcreator()
  File "c:/Users/Asus/PycharmProjects/lista de compras/lista de compras.py", line 36, in dictcreator
    d = open("dicionario.txt", "w").write(json.dumps(dict))
  File "C:\Users\Asus\AppData\Local\Programs\Python\Python38-32\lib\json\__init__.py", line 231, in dumps
    return _default_encoder.encode(obj)
  File "C:\Users\Asus\AppData\Local\Programs\Python\Python38-32\lib\json\encoder.py", line 199, in encode
    chunks = self.iterencode(o, _one_shot=True)
  File "C:\Users\Asus\AppData\Local\Programs\Python\Python38-32\lib\json\encoder.py", line 257, in iterencode
    return _iterencode(o, 0)
TypeError: keys must be str, int, float, bool or None, not Button

Мне было интересно, если кто-нибудь может сказать мне, как исправить эту ошибку: D. Я очень признателен, если кто-нибудь объяснит мне способ исправить эту ошибку.

Для лучшего понимания кода, в основном это программа для добавления / удаления / добавления элементов корзины покупок, файл "listai.txt" это массив / список всех продуктов питания. файл "listap.txt" представляет собой массив / список всех цен. В основном я создал функцию dictcreator, которая создает словарь (называемый dicionario.txt, словарь, но на португальском), получая, например, элемент 1 из listai.txt и цену 1 из listap.txt и собрать их вместе ]

listap: ["1.2", "1.9", "2.3", "3.1", "3.9"]

dicionario: {"cereja": 1.2, "банан": 1.9 "pera": 2,3, "maca": 3,1, "pesse go": 3,9}

1 Ответ

0 голосов
/ 04 апреля 2020

В python ключом словаря может быть любой хешируемый объект, а в json это может быть только str, int, float, bool or None. Попробуйте использовать dill или pickle для сохранения объектов tkinter, если вам нужно (чего не следует делать). Надеюсь, что это полезно!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...