2012-06-23 47 views
0

我試圖使用全局變量。我已經聲明它是全局的,並且在每次提到時聲明它,但是在第一個函數完成後我得到一個NameError。這是代碼,我想我已經瘋了,但我似乎無法找到問題。全局變量錯誤,儘管在每個函數中聲明變量爲全局

def on_servername_insertatcursor(self, widget): 
    global output 
    output = StringIO.StringIO()   
    servername = widget.get_text() 
    output.write("USHARE_NAME="+servername+'\n') 

def on_netif_changed(self, widget): 
    netif = widget.get_active_text() 
    global output 
    output.write("USHARE_IFACE="+netif+'\n') 

def on_port_insertatcursor(self, widget): 
    global output 
    port = widget.get_text() 
    output.write("USHARE_PORT="+port+'\n') 

def on_telprt_insertatcursor(self, widget): 
    global output 
    telprt = widget.get_text() 
    output.write("USHARE_TELNET_PORT="+telprt+'\n') 

def on_dirs_insertatcursor(self, widget): 
    global output 
    dirs = widget.get_text() 
    output.write("USHARE_DIR="+dirs+'\n') 

def on_iconv_toggled(self, widget): 
    global output 
    iconv = widget.get_active() 
    if iconv == True: 
     output.write("USHARE_OVERRIDE_ICONV_ERR="+"True"+'\n') 
    else: 
     output.write("USHARE_OVERRIDE_ICONV_ERR="+"False"+'\n') 

def on_webif_toggled(self, widget): 
    global output 
    webif = widget.get_active() 
    if webif == True: 
     output.write("USHARE_ENABLE_WEB="+"yes"+'\n') 
    else: 
     output.write("USHARE_ENABLE_WEB="+"no"+'\n') 

def on_telif_toggled(self, widget): 
    global output 
    telif = widget.get_active() 
    if telif == True: 
     output.write("USHARE_ENABLE_TELNET="+"yes"+'\n') 
    else: 
     output.write("USHARE_ENABLE_TELNET="+"no"+'\n') 

def on_xbox_toggled(self, widget): 
    global output 
    xbox = widget.get_active() 
    if xbox == True: 
     output.write("USHARE_ENABLE_XBOX="+"yes"+'\n') 
    else: 
     output.write("USHARE_ENABLE_XBOX="+"no"+'\n') 

def on_dlna_toggled(self, widget): 
    global output 
    dlna = widget.get_active() 
    if dlna == True: 
     output.write("USHARE_ENABLE_DLNA="+"yes"+'\n') 
    else: 
     output.write("USHARE_ENABLE_DLNA="+"no"+'\n') 

def on_commit_clicked(self, widget): 
    commit = output.getvalue() 
    logfile = open('/home/boywithaxe/Desktop/ushare.conf','w') 
    logfile.write(commit) 

def on_endprogram_clicked(self, widget): 
    sys.exit(0) 

令人驚歎的是,當insertatcursor(從Gtk.TextBuffer.insert_at_cursor()來)與激活替換,代碼工作完美,但我不希望有用戶需要按Enter鍵後,每數據輸入。

編輯。回溯是如下

Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line  58, in on_netif_changed 
output.write("USHARE_IFACE="+netif+'\n') 
NameError: global name 'output' is not defined 

在作出由@jdi(謝謝順便說一句,我看到背後的邏輯)建議的修改,回溯我得到的是如下:

Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 55, in on_netif_changed 
OUTPUT.write("USHARE_IFACE="+netif+'\n') 
NameError: global name 'OUTPUT' is not defined 
Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 72, in on_iconv_toggled 
OUTPUT.write("USHARE_OVERRIDE_ICONV_ERR="+"True"+'\n') 
NameError: global name 'OUTPUT' is not defined 
Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 79, in on_webif_toggled 
OUTPUT.write("USHARE_ENABLE_WEB="+"yes"+'\n') 
NameError: global name 'OUTPUT' is not defined 
Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 86, in on_telif_toggled 
OUTPUT.write("USHARE_ENABLE_TELNET="+"yes"+'\n') 
NameError: global name 'OUTPUT' is not defined 
Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 93, in on_xbox_toggled 
OUTPUT.write("USHARE_ENABLE_XBOX="+"yes"+'\n') 
NameError: global name 'OUTPUT' is not defined 
Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 100, in on_dlna_toggled 
OUTPUT.write("USHARE_ENABLE_DLNA="+"yes"+'\n') 
NameError: global name 'OUTPUT' is not defined 
Traceback (most recent call last): 
File "/home/boywithaxe/Developer/Quickly/broadcast/broadcast/BroadcastWindow.py", line 105, in on_commit_clicked 
commit = OUTPUT.getvalue() 
NameError: global name 'OUTPUT' is not defined 
+2

爲什麼你有沒有投入如此多的'全球'?此外,請張貼錯誤*的實際蹤跡,因爲這將包含原因。我懷疑'on_servername_insertatcursor'沒有被第一個調用。 – 2012-06-23 23:10:49

+3

如果你從不*分配給* output(即'output = 3'),你*不需要使它成爲全局的。 –

+1

我不認爲你去「凝視瘋狂」。我認爲你去「全球瘋狂」 – jdi

回答

1

您的代碼示例不需要全局。只要刪除它。唯一需要在函數中使用全局關鍵字的時間是如果您要分配給它。

OUTPUT = StringIO.StringIO()   

def on_servername_insertatcursor(self, widget): 
    servername = widget.get_text() 
    OUTPUT.write("USHARE_NAME="+servername+'\n') 

def on_netif_changed(self, widget): 
    netif = widget.get_active_text() 
    OUTPUT.write("USHARE_IFACE="+netif+'\n') 

def on_port_insertatcursor(self, widget): 
    port = widget.get_text() 
    OUTPUT.write("USHARE_PORT="+port+'\n') 

def on_telprt_insertatcursor(self, widget): 
    telprt = widget.get_text() 
    OUTPUT.write("USHARE_TELNET_PORT="+telprt+'\n') 

def on_dirs_insertatcursor(self, widget): 
    dirs = widget.get_text() 
    OUTPUT.write("USHARE_DIR="+dirs+'\n') 

def on_iconv_toggled(self, widget): 
    iconv = widget.get_active() 
    if iconv == True: 
     OUTPUT.write("USHARE_OVERRIDE_ICONV_ERR="+"True"+'\n') 
    else: 
     OUTPUT.write("USHARE_OVERRIDE_ICONV_ERR="+"False"+'\n') 

即使你想成爲能夠重置您的StringIO對象的功能,它仍然不會需要轉讓或全局關鍵字:

def reset_output(self): 
    OUTPUT.seek(0) 
    OUTPUT.truncate() 

證明,它的作品

import StringIO 

OUTPUT = StringIO.StringIO()   

def foo(): 
    OUTPUT.write('foo') 

def bar(): 
    OUTPUT.write('bar') 

def print_output(): 
    print OUTPUT.getvalue() 

def reset_output(): 
    OUTPUT.seek(0) 
    OUTPUT.truncate() 

if __name__ == "__main__": 
    foo() 
    bar() 
    print_output() 
    reset_output() 
    print_output() 

輸出

$ python test.py 
foobar 

$ 
+0

我曾經這樣做過,並且這給了我完全相同的Traceback。這就是我首先試用'global's的原因 – boywithaxe

+0

@boywithaxe:剛剛爲你添加了一個測試 – jdi

+0

你的示例工作完美,但是當應用於我的代碼時,它不會。我開始認爲它是小部件和它們各自的信號,否則爲什麼要在'TextBox'小部件上從'insertatcursor'改爲'activate'會影響最終結果。 – boywithaxe

0

嘗試移動output = StringIO.StringIO()以外並且高於文件中的所有功能。

0

好了,有了問題的問題是不幸的縮進:)望着PyGTK docs顯示,顯示的on_...功能的確是一個類的方法,而不是全局函數,因此,「全局」變量很可能不是真正全球化,但也該類的成員(只需查看方法定義中的self參數)。

我給了一個更詳細的回答上askubuntu,這裏的代碼片段,顯示需要做什麼:

class MyApp(gtk.Window): 

    output = None 

    def __init__(...): 
     ... 
     self.output = StringIO.StringIO() 

    def on_servername_insertatcursor(self, widget):  
     servername = widget.get_text() 
     self.output.write("USHARE_NAME="+servername+'\n') 

    def on_netif_changed(self, widget): 
     netif = widget.get_active_text() 
     self.output.write("USHARE_IFACE="+netif+'\n') 

有絕對特異性的PyGTK沒有或信號特定的魔法參與:)