質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

Tkinter

Tkinterは、GUIツールキットである“Tk”をPythonから利用できるようにした標準ライブラリである。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

Q&A

解決済

2回答

449閲覧

globalを使っているのに変数が更新されない

退会済みユーザー

退会済みユーザー

総合スコア0

Python 3.x

Python 3はPythonプログラミング言語の最新バージョンであり、2008年12月3日にリリースされました。

Tkinter

Tkinterは、GUIツールキットである“Tk”をPythonから利用できるようにした標準ライブラリである。

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2018/03/28 04:38

前提・実現したいこと

tkinterとBeautifulSoupを使って、入力したURLからリンクを取得し、listboxに表示させ、URLをクリックするとそのページに飛べるプログラムを作っています。

発生している問題・エラーメッセージ

def urlgetterでglobalを使ってurl = []を更新しようと思っているのですが、urlgetterの外でprint(urls)をすると、[]を返します。
urlgetterの中でprint(urls)をするとリンクのリストが返ってくるのでこちらはちゃんと動いでいます。
def urlgetterのurlsを外のurls = []に代入するにはどうすればいいでしょうか?

該当のソースコード

python3

1from bs4 import BeautifulSoup 2from tkinter import * 3from tkinter import ttk 4import urllib.request 5import webbrowser 6 7urls = [] 8 9def urlgetter(oneurl): 10 global urls 11 try: 12 oneurl = str(oneurl) 13 except ValueError: 14 return entry.delete(0, END) 15 html = urllib.request.urlopen(oneurl) 16 soup = BeautifulSoup(html, "lxml") 17 hrefs = [] 18 for link in soup.find_all("a"): 19 hrefs.append(link.get("href")) 20 hrefs = filter(None, hrefs) 21 pat = "http" 22 for links in hrefs: 23 if pat in links: 24 urls.append(links) 25 return urls 26 27def urljump(evt): 28 wgt = evt.widget 29 print(wgt) 30 idx = wgt.curselection()[0] 31 url = wgt.get(idx) 32 webbrowser.open_new(url) 33 34root = Tk() 35root.title(u'Url Getter') 36root.geometry("300x300") 37 38frame = Frame(root) 39frame.grid() 40 41entry = Entry(frame) 42entry.bind("<Return>", lambda event:urlgetter(entry.get())) 43entry.grid(row=0) 44 45listbox1 = Listbox(frame, width=30) 46for url in urls: 47 listbox1.insert(END, url) 48listbox1.bind("<<ListboxSelet>>", urljump) 49listbox1.grid(row=1, column=0) 50 51scrollbar = Scrollbar(frame, orient=VERTICAL, command=listbox1.yview) 52listbox1['yscrollcommand'] = scrollbar.set 53scrollbar.grid(row=1, column=1, sticky=(N,S)) 54 55root.mainloop()

試したこと

ここに問題に対して試したことを記載してください。

補足情報(FW/ツールのバージョンなど)

ここにより詳細な情報を記載してください。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

ベストアンサー

まず誤字<<ListboxSelet>>"<<ListboxSelect>>"に修正しないとリストボックスのイベントが呼ばれません。
また、リストボックス構築時に項目を追加する処理において、まだurlsは空なので無意味です。
urlgetter内で行う必要があります。

以上を踏まえて修正したソースです。
細かい動作は確認していませんが、ひととおり動作します。

Python

1from bs4 import BeautifulSoup 2from tkinter import * 3from tkinter import ttk 4import urllib.request 5import webbrowser 6 7listbox1 = None 8 9def urlgetter(oneurl): 10 listbox1.delete(0,END) # ListBoxの項目を全削除 11 try: 12 oneurl = str(oneurl) 13 except ValueError: 14 return entry.delete(0, END) 15 html = urllib.request.urlopen(oneurl) 16 soup = BeautifulSoup(html, "lxml") 17 hrefs = [] 18 for link in soup.find_all("a"): 19 hrefs.append(link.get("href")) 20 hrefs = filter(None, hrefs) 21 pat = "http" 22 for links in hrefs: 23 if pat in links: 24 listbox1.insert(END, links) 25 26def urljump(evt): 27 wgt = evt.widget 28 print(wgt) 29 idx = wgt.curselection()[0] 30 url = wgt.get(idx) 31 webbrowser.open_new(url) 32 33root = Tk() 34root.title(u'Url Getter') 35root.geometry("300x300") 36 37frame = Frame(root) 38frame.grid() 39 40entry = Entry(frame) 41entry.bind("<Return>", lambda event:urlgetter(entry.get())) 42entry.grid(row=0) 43 44listbox1 = Listbox(frame, width=30) 45listbox1.bind("<<ListboxSelect>>", urljump) # "<<ListboxSelet>>" 誤字修正 46# ここでのURLリスト追加は無意味 47listbox1.grid(row=1, column=0) 48 49scrollbar = Scrollbar(frame, orient=VERTICAL, command=listbox1.yview) 50listbox1['yscrollcommand'] = scrollbar.set 51scrollbar.grid(row=1, column=1, sticky=(N,S)) 52 53root.mainloop()

投稿2018/03/28 05:16

can110

総合スコア38233

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2018/03/28 06:11

ありがとうございました!
guest

0

まずぶっちゃけると、global宣言はこの場合あってもなくても動きます。

python

1>>> lst = [] 2>>> def hoge(): 3... lst.append("hoge") 4... 5>>> lst 6[] 7>>> hoge() 8>>> lst 9['hoge']

理由は、別に代入はしてなくてメソッド呼んでるだけだからです。そんな感じ。

恐らく、動かない原因はそこではないでしょう。

投稿2018/03/28 04:54

hayataka2049

総合スコア30933

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問