Python 属性错误:'_tkinter.tkapp';对象没有属性';文本';在特金特

Python 属性错误:'_tkinter.tkapp';对象没有属性';文本';在特金特,python,python-3.x,tkinter,error-handling,Python,Python 3.x,Tkinter,Error Handling,我设置了一个天气应用程序,但当我点击按钮获取天气时,我得到了这个错误?在这个应用程序中,我创建了线程,用于进行后台处理。 在这里,我试图在另一个函数中获取self.text值和访问权限 错误: class App(tk.Tk): def __init__(self, *args, **kwargs): tk.Tk().__init__(self, *args, **kwargs) super().__init__() self.titl

我设置了一个天气应用程序,但当我点击按钮获取天气时,我得到了这个错误?在这个应用程序中,我创建了
线程
,用于进行后台处理。 在这里,我试图在另一个函数中获取
self.text
值和访问权限

错误:

class App(tk.Tk):
    def __init__(self, *args, **kwargs):
        tk.Tk().__init__(self, *args, **kwargs)

        super().__init__()

        self.title('AccWeather')
        self.geometry('600x500')
import requests
from tkinter import *
from bs4 import BeautifulSoup
from threading import  Thread
from io import BytesIO
from PIL import ImageTk, Image

class gui(Tk):
    def __init__(self):
        Tk.__init__(self)

        # title of app
        self.title('AccWeather')
        self.geometry('600x500')

        # API
        self.api = 'cKh5lrrqb7L26PC9OFyuj1S1y14oPMCh'

        # main canvas with image
        url = 'https://images.unsplash.com/photo-1451154488477-d20dee2a4e46?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=753&q=80'
        img = requests.get(url).content
        self.img = ImageTk.PhotoImage(Image.open(BytesIO(img)))
        self.main = Label(self, image=self.img)
        self.main.place(relx=.0, rely=.0, relwidth=1, relheight=1)




        # button and input
        self.city = Entry(self.main, bd=0, font=3, fg='black')
        self.city.place(relx=0.1, rely=0.1, relheight=0.1, relwidth=0.6)
        Button(self.main, text='Get Weather', bg='DodgerBlue',font=5, bd=1, command=self.get_weather_call).place(relx=0.7, rely=.1, relheight=0.1,relwidth=0.2)

        # API box
        Label(self.main, bg='white', text='API key: ').place(relx=0.1, rely=0)
        self.api_box = Entry(self.main, bd=1, font=2)
        self.api_box.place(relx=0.2, rely=0, relwidth=.7)
        self.api_box.insert(0, self.api)


        # output label
        Label(self.main, text='OUTPUT:', fg='black',bg='white', font=5).place(relx=.1, rely=.3)
        # output box
        self.put_out = Label(self.main, font=20, anchor='nw', bg='white', justify='left', bd=5)  # border = bd
        self.put_out.place(relx=.1, rely=.4, relwidth=.8, relheight=.5)


        # weather icon
        self.icon = Label(self.main, height=200, width=200, bg='white')
        self.icon.place(relx=.7, rely=.4, relwidth=.2, relheight=.2)
        self.photo = None



    def get_weather_call(self):
       city = self.city.get()

        thread1 = Thread(target=self.get_weather, args=(city,))
        thread1.start()

        text = self.text

        thread_weather_icon = Thread(target=self.weather_icon, args=(text,))
        thread_weather_icon.start()


    def get_weather(self, city):
        # autocomplete location
        try:
            auto_url = f"http://dataservice.accuweather.com/locations/v1/cities/autocomplete?apikey={self.api}&q=" + city
            data = requests.get(auto_url).json()
            check = ''
            for i in data:
                for a in i:
                    if a=='ServiceUnavailable':
                        check = True
            if  check:
                self.put_out['text'] = 'Error: '+data['Message']
            else:
                try:
                    key = data[0]['Key']
                    city_name = ', '.join([data[0]['LocalizedName'], data[0]['Country']['LocalizedName']])
                    api = requests.get(f"http://dataservice.accuweather.com/currentconditions/v1/{key}?apikey={self.api}").json()

                    temp = api[0]['Temperature']['Metric']['Value']
 This is self----> self.text = api[0]['WeatherText']
                    weather = f'City: {city_name}\nTemperature (c): {int(temp)}\nCondition: {self.text}'
                    self.put_out['text'] = weather

                except Exception as e:
                    self.put_out['text'] = e
        except Exception as e:
            print(e)

    def weather_icon(self, txt):
        split = txt.split(' ')
        get_text = '+'.join(split)
        print(get_text)
        url = 'https://www.iconfinder.com/search/?q='+get_text
        req = requests.get(url).content
        soup = BeautifulSoup(req, 'html.parser')
        img_url = soup.find('img', {'class': 'd-block'})['src']
        image_content = requests.get(img_url).content
        self.photo = ImageTk.PhotoImage(Image.open(BytesIO(image_content)))
        self.icon['image'] = self.photo



if __name__ == '__main__':
    start = gui()
    start.mainloop()

线程天气图标=线程(目标=self.weather图标, args=(self.text,))文件 “C:\Users\ABC\AppData\Local\Programs\Python37-32\lib\tkinter\uuuu init\uuuuu.py”, 第2101行,在getattr return getattr(self.tk,attr)AttributeError:“\u tkinter.tkapp”对象没有属性“text”

我不知道我为什么会犯这个错误

我已尝试更改此设置,但仍然遇到错误:

class App(tk.Tk):
    def __init__(self, *args, **kwargs):
        tk.Tk().__init__(self, *args, **kwargs)

        super().__init__()

        self.title('AccWeather')
        self.geometry('600x500')
import requests
from tkinter import *
from bs4 import BeautifulSoup
from threading import  Thread
from io import BytesIO
from PIL import ImageTk, Image

class gui(Tk):
    def __init__(self):
        Tk.__init__(self)

        # title of app
        self.title('AccWeather')
        self.geometry('600x500')

        # API
        self.api = 'cKh5lrrqb7L26PC9OFyuj1S1y14oPMCh'

        # main canvas with image
        url = 'https://images.unsplash.com/photo-1451154488477-d20dee2a4e46?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=753&q=80'
        img = requests.get(url).content
        self.img = ImageTk.PhotoImage(Image.open(BytesIO(img)))
        self.main = Label(self, image=self.img)
        self.main.place(relx=.0, rely=.0, relwidth=1, relheight=1)




        # button and input
        self.city = Entry(self.main, bd=0, font=3, fg='black')
        self.city.place(relx=0.1, rely=0.1, relheight=0.1, relwidth=0.6)
        Button(self.main, text='Get Weather', bg='DodgerBlue',font=5, bd=1, command=self.get_weather_call).place(relx=0.7, rely=.1, relheight=0.1,relwidth=0.2)

        # API box
        Label(self.main, bg='white', text='API key: ').place(relx=0.1, rely=0)
        self.api_box = Entry(self.main, bd=1, font=2)
        self.api_box.place(relx=0.2, rely=0, relwidth=.7)
        self.api_box.insert(0, self.api)


        # output label
        Label(self.main, text='OUTPUT:', fg='black',bg='white', font=5).place(relx=.1, rely=.3)
        # output box
        self.put_out = Label(self.main, font=20, anchor='nw', bg='white', justify='left', bd=5)  # border = bd
        self.put_out.place(relx=.1, rely=.4, relwidth=.8, relheight=.5)


        # weather icon
        self.icon = Label(self.main, height=200, width=200, bg='white')
        self.icon.place(relx=.7, rely=.4, relwidth=.2, relheight=.2)
        self.photo = None



    def get_weather_call(self):
       city = self.city.get()

        thread1 = Thread(target=self.get_weather, args=(city,))
        thread1.start()

        text = self.text

        thread_weather_icon = Thread(target=self.weather_icon, args=(text,))
        thread_weather_icon.start()


    def get_weather(self, city):
        # autocomplete location
        try:
            auto_url = f"http://dataservice.accuweather.com/locations/v1/cities/autocomplete?apikey={self.api}&q=" + city
            data = requests.get(auto_url).json()
            check = ''
            for i in data:
                for a in i:
                    if a=='ServiceUnavailable':
                        check = True
            if  check:
                self.put_out['text'] = 'Error: '+data['Message']
            else:
                try:
                    key = data[0]['Key']
                    city_name = ', '.join([data[0]['LocalizedName'], data[0]['Country']['LocalizedName']])
                    api = requests.get(f"http://dataservice.accuweather.com/currentconditions/v1/{key}?apikey={self.api}").json()

                    temp = api[0]['Temperature']['Metric']['Value']
 This is self----> self.text = api[0]['WeatherText']
                    weather = f'City: {city_name}\nTemperature (c): {int(temp)}\nCondition: {self.text}'
                    self.put_out['text'] = weather

                except Exception as e:
                    self.put_out['text'] = e
        except Exception as e:
            print(e)

    def weather_icon(self, txt):
        split = txt.split(' ')
        get_text = '+'.join(split)
        print(get_text)
        url = 'https://www.iconfinder.com/search/?q='+get_text
        req = requests.get(url).content
        soup = BeautifulSoup(req, 'html.parser')
        img_url = soup.find('img', {'class': 'd-block'})['src']
        image_content = requests.get(img_url).content
        self.photo = ImageTk.PhotoImage(Image.open(BytesIO(image_content)))
        self.icon['image'] = self.photo



if __name__ == '__main__':
    start = gui()
    start.mainloop()

我的代码:

class App(tk.Tk):
    def __init__(self, *args, **kwargs):
        tk.Tk().__init__(self, *args, **kwargs)

        super().__init__()

        self.title('AccWeather')
        self.geometry('600x500')
import requests
from tkinter import *
from bs4 import BeautifulSoup
from threading import  Thread
from io import BytesIO
from PIL import ImageTk, Image

class gui(Tk):
    def __init__(self):
        Tk.__init__(self)

        # title of app
        self.title('AccWeather')
        self.geometry('600x500')

        # API
        self.api = 'cKh5lrrqb7L26PC9OFyuj1S1y14oPMCh'

        # main canvas with image
        url = 'https://images.unsplash.com/photo-1451154488477-d20dee2a4e46?ixlib=rb-1.2.1&ixid=eyJhcHBfaWQiOjEyMDd9&auto=format&fit=crop&w=753&q=80'
        img = requests.get(url).content
        self.img = ImageTk.PhotoImage(Image.open(BytesIO(img)))
        self.main = Label(self, image=self.img)
        self.main.place(relx=.0, rely=.0, relwidth=1, relheight=1)




        # button and input
        self.city = Entry(self.main, bd=0, font=3, fg='black')
        self.city.place(relx=0.1, rely=0.1, relheight=0.1, relwidth=0.6)
        Button(self.main, text='Get Weather', bg='DodgerBlue',font=5, bd=1, command=self.get_weather_call).place(relx=0.7, rely=.1, relheight=0.1,relwidth=0.2)

        # API box
        Label(self.main, bg='white', text='API key: ').place(relx=0.1, rely=0)
        self.api_box = Entry(self.main, bd=1, font=2)
        self.api_box.place(relx=0.2, rely=0, relwidth=.7)
        self.api_box.insert(0, self.api)


        # output label
        Label(self.main, text='OUTPUT:', fg='black',bg='white', font=5).place(relx=.1, rely=.3)
        # output box
        self.put_out = Label(self.main, font=20, anchor='nw', bg='white', justify='left', bd=5)  # border = bd
        self.put_out.place(relx=.1, rely=.4, relwidth=.8, relheight=.5)


        # weather icon
        self.icon = Label(self.main, height=200, width=200, bg='white')
        self.icon.place(relx=.7, rely=.4, relwidth=.2, relheight=.2)
        self.photo = None



    def get_weather_call(self):
       city = self.city.get()

        thread1 = Thread(target=self.get_weather, args=(city,))
        thread1.start()

        text = self.text

        thread_weather_icon = Thread(target=self.weather_icon, args=(text,))
        thread_weather_icon.start()


    def get_weather(self, city):
        # autocomplete location
        try:
            auto_url = f"http://dataservice.accuweather.com/locations/v1/cities/autocomplete?apikey={self.api}&q=" + city
            data = requests.get(auto_url).json()
            check = ''
            for i in data:
                for a in i:
                    if a=='ServiceUnavailable':
                        check = True
            if  check:
                self.put_out['text'] = 'Error: '+data['Message']
            else:
                try:
                    key = data[0]['Key']
                    city_name = ', '.join([data[0]['LocalizedName'], data[0]['Country']['LocalizedName']])
                    api = requests.get(f"http://dataservice.accuweather.com/currentconditions/v1/{key}?apikey={self.api}").json()

                    temp = api[0]['Temperature']['Metric']['Value']
 This is self----> self.text = api[0]['WeatherText']
                    weather = f'City: {city_name}\nTemperature (c): {int(temp)}\nCondition: {self.text}'
                    self.put_out['text'] = weather

                except Exception as e:
                    self.put_out['text'] = e
        except Exception as e:
            print(e)

    def weather_icon(self, txt):
        split = txt.split(' ')
        get_text = '+'.join(split)
        print(get_text)
        url = 'https://www.iconfinder.com/search/?q='+get_text
        req = requests.get(url).content
        soup = BeautifulSoup(req, 'html.parser')
        img_url = soup.find('img', {'class': 'd-block'})['src']
        image_content = requests.get(img_url).content
        self.photo = ImageTk.PhotoImage(Image.open(BytesIO(image_content)))
        self.icon['image'] = self.photo



if __name__ == '__main__':
    start = gui()
    start.mainloop()


请,我能理解。

self.weather图标
需要
self.text
,它是在
self.get\u weather
中创建的,因此
self.get\u weather
必须在
self.weather图标
之前运行,并且
self.weather图标
必须等待
self.get\u weather
结束其工作-确保
self.text
已存在

最好将两个函数中的代码放在一个函数中,并在一个线程中运行

def get_weather_call(self):
    city = self.city.get()
    thread = Thread(target=self.get_weather_and_icon, args=(city,))
    thread1.start()

    thread_weather_icon = Thread(target=self.weather_icon, args=(self.text,))
    thread_weather_icon.start()


def get_weather_and_icon(self, city):
    # autocomplete location
    try:
        auto_url = f"http://dataservice.accuweather.com/locations/v1/cities/autocomplete?apikey={self.api}&q=" + city
        data = requests.get(auto_url).json()
        check = ''
        for i in data:
            for a in i:
                if a=='ServiceUnavailable':
                    check = True
        if  check:
            self.put_out['text'] = 'Error: '+data['Message']
        else:
            try:
                key = data[0]['Key']
                city_name = ', '.join([data[0]['LocalizedName'], data[0]['Country']['LocalizedName']])
                api = requests.get(f"http://dataservice.accuweather.com/currentconditions/v1/{key}?apikey={self.api}").json()

                temp = api[0]['Temperature']['Metric']['Value']
                self.text = api[0]['WeatherText']
                weather = f'City: {city_name}\nTemperature (c): {int(temp)}\nCondition: {self.text}'
                self.put_out['text'] = weather

            except Exception as e:
                self.put_out['text'] = e
    except Exception as e:
        print(e)

    split = self.text.split(' ')
    get_text = '+'.join(split)
    print(get_text)
    url = 'https://www.iconfinder.com/search/?q='+get_text
    req = requests.get(url).content
    soup = BeautifulSoup(req, 'html.parser')
    img_url = soup.find('img', {'class': 'd-block'})['src']
    image_content = requests.get(img_url).content
    self.photo = ImageTk.PhotoImage(Image.open(BytesIO(image_content)))
    self.icon['image'] = self.photo

哪里是self.text=…?您没有
self.text
,因此不能将其用作参数。我有。你又看到了代码。现在我看到你在
self.get_weather
中看到了它,但是它是在
线程(target=self.weather\u图标,args=(self.text,)
之后执行的,所以
self.text
创建得太晚了。您必须首先运行self.get_weather并等待它创建self.text是否正确:
text=self.text
!你必须先运行self.get_weather并等待它创建self.text,然后运行Thread(target=self.weather_图标,args=(self.text,)我们能在一个人身上见面吗?