首先看一段**:
a =0b =[0]
deffun1(a, b):
a += 1b[0] += 1fun1(a, b)
'after fun1 %d %s
' %(a,b)
deffun2():
global
a a += 1b[0] += 1fun2()
'after fun2 %d %s
' % (a,b)
執行後的結果:
after fun1 0 [1]after fun2 1 [2]
fun1中,a作為基本型別(int)是值傳遞,b不是基本型別(list)則是引用傳遞,所以執行後全域性的a未變但b變了;
(如果熟悉c++就很容易理解,類似的概念:指標、引用、深拷貝、淺拷貝等)
(注意,與c++不同,python中字串str為基本型別)
fun2中,使用python的關鍵字global才可以在函式內操作全域性變數a,但b不需要global卻能直接使用,這樣可以避免一些「自以為是」的邏輯錯誤;
(注意,如果僅僅訪問而不修改,在函式內是可以不用global直接使用的,比如在fun2中只是print a)
有了上面的理解後,我們來分析下在python中怎麼用全域性變數好:
首先,使用基本型別的全域性變數需要在每個操作它的函式、類裡面用global宣告還是挺麻煩的;
列表或元組呢,訪問的時候用數字索引會降低**的可讀性;
用字典(dict)則可以解決上面兩個問題,在簡單的程式中dict應該是很合適的;
但是,在複雜的**中如果需要對全域性變數的修改進行一定的控制,或者在多組多個執行緒每組共享同型別但不同值的全域性變數時,dict就無法勝任;
綜上,個人認為自定義乙個類來儲存所有的全域性變數是最好的方法:
簡單時就直接訪問成員變數;
需要控制時就宣告為私有變數,用成員函式訪問和修改;
多組多執行緒分開共享時就每組new乙個新例項即可;
示例一:
#common.py
class
myglobal:
def__init__
(self):
self.a =0
self.b =[0]
gl =myglobal()
#main.py
from common import *
deffun():
gl.a += 1gl.b[0] += 1fun()
'after fun %d %s
' %(gl.a,gl.b)
#執行./main.py
after fun 1 [1]
示例二:
#common.py
import
threading
class
myglobal:
def__init__
(self, i, setname):
self.setname =setname
self.a =i
self.b =[i]
#main.py
from common import *
deffun_trd(gl):
'%s %d %s
' %(gl.setname,gl.a,gl.b)
#兩組,每組三個執行緒
trds =
for i in range(0,2):
setname = '
set%d
' %i
gl =myglobal(i, setname)
for k in range(0,3):
t = threading.thread(target=fun_trd, args=(gl,))
t.setdaemon(true)
t.start()
for t in
trds:
t.join()
#執行./main.py
set0 0 [0]
set0 0 [0]
set0 0 [0]
set1 1 [1]
set1 1 [1]
set1 1 [1]
over
python中全域性變數
在python中,全域性變數一般有兩種使用方式 第一種 是在乙個單獨的模組中定義好,然後在需要使用的全域性模組中將定義的全域性變數模組匯入。第二種 直接在當前的模組中定義好,然後直接在本模組中通過global宣告,然後使用 具體的方法如下所示 第一種 solr url def tt global s...
Python中的全域性變數
全域性變數不符合引數傳遞的精神,所以,平時我很少使用,除非定義常量。今天有同事問乙個關於全域性變數的問題,才發現其中原來還有門道。程式大致是這樣的 constant 0 def modifyconstant print constant constant 1 return if name main ...
python 全域性變數
應該盡量避免使用全域性變數。不同的模組都可以自由的訪問全域性變數,可能會導致全域性變數的不可預知性。對全域性變數,如果程式設計師甲修改了 a的值,程式設計師乙同時也要使用 a,這時可能導致程式中的錯誤。這種錯誤是很難發現和更正的。全域性變數降低了函式或模組之間的通用性,不同的函式或模組都要依賴於全域...