2017-03-07 140 views
1

以下哪種情況是在python中聲明實例變量的最佳實踐方式。是否有典型的偏好,這有什麼理由?在哪裏聲明對象變量

選項1 - __init__

class MyObject: 

    def __init__(self, arg): 
     self.variable_1 = self.method_1(arg) 

    def method_1(self, arg): 
     return(arg) 

方案2中聲明 - 聲明在其他方法

class MyObject: 

    def __init__(self, arg): 
     self.method_1(arg) 

    def method_1(self, arg): 
     self.variable_1 = arg 

這純粹是爲了瞭解是否有這樣做的最佳實踐方法其他開發人員更願意在查看和擴展代碼時看到。

+0

選項1.你應該在'__init__'中聲明所有的屬性,因爲它在哪裏有人會尋找它們。 –

+0

OOP中的一般規則(不考慮編程語言)是構造函數就像__init__中的賦值操作符意味着我們應該分配實例變量的值。所以我認爲我們應該在__init__中賦值,getter和setter應該與它分開。 –

+2

我爲迂腐而道歉,但實例變量沒有在Python中聲明。當它們首次被分配時,它們[彈出](https://docs.python.org/3.3/tutorial/classes.html#instance-objects)。變量聲明存在於C++和Java等語言中,而不是Python中。 –

回答

0

這顯然不是精確的科學,但在構造函數中設置所有屬性(儘可能)通常更有意義,以便您可以跟蹤它們。

當然,您可以稍後在其他方法中根據需要更改它們。

設置類中的構造函數級別變量使得很難理解事物來自哪裏。

0

選項1是在Python中聲明實例變量的最佳實踐。 實例變量適用於實際上是實例的一部分的數據,所以如果您在構造函數中定義,它會更好。

0

你的選擇2基本上是一個Setter-/Getter-Paradigm。 Python使用這些用例的屬性。對於類似的問題,還有一個不錯的SO-answer

一般來說,你初始化所有的實例變量在__init__-方法,這就是它存在的原因。如果你需要一個getter-/setter使用屬性。並使用「最少驚訝」的原則。不要驚訝另一位讀者,或者你以後的自己過於聰明和/或複雜的解決方案。 (又名KISS原則)

0

這要看。定義__init__本身內的所有屬性通常會使代碼更具可讀性,但如果類具有很多屬性,並且可以輕鬆將它們劃分爲邏輯組,那麼使用它自己的初始化方法初始化每組屬性是有意義的。您可能希望通過給他們一個以單個下劃線開始的名稱來指示這樣的方法是private

請注意,如果該類是從一個或多個其他類派生的(除了object),則必須調用super.__init__來初始化從父類繼承的屬性。

底線是所有實例屬性在__init__完成執行時應該存在。如果無法爲__init__中的某個屬性設置適當的值,則應將其設置爲適當的默認值,例如空字符串,列表等,None或哨點值,如object()

當然,上述內容不適用於@property屬性,但即使這些屬性通常具有應在__init__中設置的基礎「私有」屬性。

有關房產的更多信息,請參閱Raymond Hettinger的優秀Descriptor HowTo Guide在Python文檔中。


由於juanpa.arrivillaga在問題的評論中提到,我們實際上並不在Python聲明變量。這基本上是因爲Python數據模型並沒有像C和許多其他語言那樣的變量。請參閱Other languages have "variables", Python has "names"以獲得簡潔的解釋。另見Facts and myths about Python names and values,這是由SO經驗豐富的Ned Batchelder編寫的。