2013-01-16 103 views
7

如何從另一個函數內部的函數內設置類變量?Python作用域內的嵌套函數內的作用域?

var.py

class A: 
    def __init__(self): 
     self.a = 1 
     self.b = 2 
     self.c = 3 
    def seta(self): 
     def afunction(): 
      self.a = 4 
     afunction() 
    def geta(self): 
     return self.a 

run.py

cA = A() 
print cA.a 
cA.seta() 
print cA.a 
print cA.geta() 

蟒蛇run.py

1 
1 
1 

爲什麼一個不等於4,以及如何我可以使其等於4?

謝謝

對不起,我原來的代碼作爲功能稱爲 - 忘了。

編輯:

謝謝大家 - 對不起,我剛纔看到了。我不小心被我的一個名字中的一個......所以我的範圍實際上都沒問題。

+3

你甚至沒有在代碼中調用'afunction()'。 –

+6

您不應將您的代碼更改爲答案。這是無益的,如果我們必須查看修訂,看看回答了什麼問題。 – TheHerk

回答

6

問題是,有多個self變量。傳遞給你的內部函數的參數會覆蓋外部的範圍。

您可以通過從內部函數中刪除self參數並確保以某種方式調用該函數來克服此問題。

class A: 
    def __init__(self): 
     self.a = 1 
     self.b = 2 
     self.c = 3 
    def seta(self): 
     def afunction(): # no self here 
      self.a = 4 
     afunction()  # have to call the function 
    def geta(self): 
     return self.a 
1

裏面seta,你定義一個函數

def afunction(self): 
     self.a = 4 

...這設置self.a 4,如果它都不會被調用。但它並沒有被調用,所以a沒有改變。

2

正如其他人所說,afunction永遠不會被調用。你可以做這樣的事情:

class A: 
    def __init__(self): 
     self.a = 1 

    def seta(self): 
     def afunction(self): 
      self.a = 4 
     afunction(self) 

    def geta(self): 
     return self.a 

a = A() 
print a.a 
a.seta() 
print a.a 

在這裏,我們實際調用afunction,並明確地傳遞self,但這是設置屬性a一個相當愚蠢的方式 - 尤其是當我們可以明確地做到這一點,而不需要干將或setter方法:a.a = 4

或者你可以return功能:

def seta(self): 
    def afunction(): #Don't need to pass `self`. It gets picked up from the closure 
     self.a = 4 
    return afunction 

,然後在代碼:

a = A() 
a.seta()() #the first call returns the `afunction`, the second actually calls it. 
-1

正如一些人所說,你需要實際呼叫泛函在一些點。評論不會讓我intelligably鍵入此所以這裏有一個答案:

def seta(self): 
    def functiona(self): #defined 
     self.a = 4 
    functiona()   #called 
+0

這不應該起作用。至少在Python 3中,你會得到一個錯誤'缺少1個必需的位置參數:'self'。你需要調用'functiona(self)',但是這個解決方案對於定義嵌套函數是多餘的。 – Yeo

+0

您沒有注意到這是在原始問題的類範圍內定義了某些內容。 –

0

你怎麼可以把它等同於4:

class A: 
    def __init__(self): 
     self.a = 1 
     self.b = 2 
     self.c = 3 
    def seta(self): 
     ##def afunction(self): (remove this) 
     self.a = 4 
    def geta(self): 
     return self.a 

棘手的部分:爲什麼不等同於4 ...

當前a僅通過「功能」設置爲4。因爲函數從來沒有被調用過,所以它永遠不會執行。seta有嵌套在裏面但不被調用的「函數」...類似於類中的成員變量。