PyQtライブラリを使用してWebページのスクリーンショットを撮り、さまざまなURLのCSVファイルを読んでいます。 URLが処理されるたびに増加する可変フィードを保持しているため、URLの数に応じて増加します。
コードは次のとおりです。
webpage = QWebPage()
fo = open("C:/Users/Romi/Desktop/result1.txt", "w")
feed = 0
def onLoadFinished(result):
#fo.write( column1[feed])#, column2[feed], urls[feed])
#feed = 0
if not result:
print "Request failed"
fo.write(column1[feed])
fo.write(',')
fo.write(column2[feed])
fo.write(',')
#fo.write(urls[feed])
fo.write(',')
fo.write('404,image not created\n')
feed = feed + 1
sys.exit(1)
save_page(webpage, outputs.pop(0)) # pop output name from list and save
if urls:
url = urls.pop(0) # pop next url to fetch from list
webpage.mainFrame().load(QUrl(url))
fo.write(column1[feed])#,column2[feed],urls[feed],'200','image created','/n')
fo.write(',')
fo.write(column2[feed])
fo.write(',')
#fo.write(urls[feed])
fo.write(',')
fo.write('200,image created\n')
feed = feed + 1
else:
app.quit() # exit after last url
webpage.connect(webpage, SIGNAL("loadFinished(bool)"), onLoadFinished)
webpage.mainFrame().load(QUrl(urls.pop(0)))
#fo.close()
sys.exit(app.exec_())
それは私にエラーを与えます:
local variable feed referenced before the assignment at fo.write(column1[feed])#,column2[feed],urls[feed],'200','image created','/n')
理由は何ですか?
Pythonが関数定義の本体を解析し、次のような割り当てに遭遇したとき
feed = ...
Pythonはfeed
をデフォルトでローカル変数として解釈します。ローカル変数にしたくない場合は、
global feed
関数定義で。グローバルステートメントは、関数定義の先頭にある必要はありませんが、通常はそこに配置されます。どこに配置されても、グローバル宣言はfeed
をグローバル変数everywhereにします。
グローバルステートメントがない場合、Pythonが実行されると、feed
がローカル変数と見なされるため
feed = feed + 1,
Pythonは最初に右側を評価し、フィードの値を検索しようとします。最初にfeed
が未定義であることがわかりました。したがって、エラー。
コードを修正する最短の方法は、global feed
をonLoadFinished
の先頭に追加することです。より良い方法は、クラスを使用することです:
class Page(object):
def __init__(self):
self.feed = 0
def onLoadFinished(self, result):
...
self.feed += 1
グローバル変数を変更する関数を持つことの問題は、コードを理解するのが難しくなることです。関数はもはや孤立したユニットではありません。それらの相互作用は、グローバル変数に影響を与えるか、またはグローバル変数の影響を受けるすべてに拡張されます。したがって、大きなプログラムを理解するのが難しくなります。
グローバルの変更を回避することにより、長期的にはコードの理解、テスト、保守が容易になります。
関数の先頭にグローバルステートメントを配置すると、うまくいくはずです。
def onLoadFinished(result):
global feed
...
私が意味することを実証するために、この小さなテストを見てください。
x = 0
def t():
x += 1
t()
これは、次の場合とまったく同じエラーで爆発します。
x = 0
def t():
global x
x += 1
t()
ではない。
その理由は、t
の内部で、Pythonはx
がローカル変数であると考えるからです。さらに、x
がグローバルであることを明示的に伝えない限り、x += 1
でx
という名前のローカル変数を使用しようとします。ただし、x
のローカルスコープにt
が定義されていないため、エラーがスローされます。
Pythonインタープリターが関数の定義(または、インデントされたコードのブロックですら)を読み取ると、に割り当てられているすべての変数が関数内で、その関数のローカルに追加されます。ローカルに割り当ての前に定義がない場合、Pythonインタープリターは何をすべきかを知らないため、このエラーがスローされます。
ここでの解決策は、追加することです
global feed
フィード変数がこの関数に対してローカルではないことをインタープリターに示すために、関数(通常は上部近く)に追加します。