2013-05-01 142 views
2

這是不好的編程習慣,是的,我知道,但這些腳本純粹是我的,這種技術會減輕我的編碼很多。從變量設置類(自)變量?

現在,我有一個SQLite數據庫,其中包含一組鍵值對,代表我的腳本的配置指令。腳本本身是一個我導入其他腳本的類。

所以,現在,當我想訪問一個配置變量,我稱之爲是這樣的:

myLib.myClass.getConfigVariable("theItemIWant") 

在腳本中使用配置變量時,這變得非常難看。

所以我想簡化對這些變量的訪問。

myLib.myClass.config['theItemIWant'] 

但我更優雅的思維甚至有點:我可以用一本字典,當類加載並做預填充。我編寫了一個單獨的配置類,我想提供對配置條目的可變級別訪問。

所以我希望能夠做的是:

myLib.Config().theItemIWant 

還是要在這樣的腳本實例化一個對象:

def myRoutine(self): 
    cfg = myLib.Config() 
    print cfg.theItemIWant 

我讀過有關醜(使用EXEC)方法來實現這一點,而我其實可以,但我無法弄清楚如何以這種方式設置CLASS級變量。大多數人建議使用exec或改變變量或全局變量,但我不確定這是否會直接在Config類中設置變量,而不是在其他地方。

使用EXEC失敗:

SyntaxError: unqualified exec is not allowed in function '__init__' it contains a nested function with free variables 

因此,我認爲這樣做的唯一方法是改變瓦爾(),但我不知道如何適用於類。

+0

目前還不清楚你想要做什麼,或者你爲什麼要使用'exec',尤其是因爲你沒有展示一個完整的例子。如果你想設置一個成員變量,只需設置它。 – Marcin 2013-05-01 17:27:29

+0

你可以用'exec'來舉一個你的代碼的例子嗎?目前還不清楚你想要達到的目標。爲什麼你不能'myLib.config.theItemIWant = whatever'? – BrenBarn 2013-05-01 17:27:52

+0

[從用戶輸入創建動態命名變量](http://stackoverflow.com/questions/11354214/creating-dynamically-named-variables-from-user-input) – Marcin 2013-05-01 17:52:59

回答

2

你可以簡單地實現__getattr__()功能,爲您的配置對象像

def __getattr__(self, name): 
    if name in self.items: 
     return self.items[name] 
    else: 
     raise AttributeError() 

here的Python文檔爲__getattr__()描述。

+0

這是拼寫'__getattr__' – 2013-05-01 17:33:31

+0

@FrancisAvila thx!糾正。 – MartinStettner 2013-05-01 17:34:56

+1

或者使用'setattr'運算符。 – Marcin 2013-05-01 17:53:34

1

我想你想的只是分配給一個成員變量,像這樣的內容:

class Foo(object): 
     pass 

cfg = Foo() 
cfg.item_i_want = "An item" 
print cfg.item_i_want 

這將打印「的項目」。請參閱:http://ideone.com/LDz7NK

如果要動態選擇變量名稱,請使用setattr(cfg, "another_item_i_want", "another item")

+0

這種方式你不能設置屬性「動態「從你的數據庫條目... – MartinStettner 2013-05-01 17:33:45

2

一種試圖不重新發明車輪的解決方案。當你只想讀取配置一次,並且它的結構是平坦的。

from collections import namedtuple 

def getConfig(config_source): 
    # read the config_source into a dict 
    # config_source might be a file name or whatnot 
    config_dict = read_somehow(config_source) 
    tuple_class = namedtuple('Config', config_dict.keys()) 
    return tuple_class(**config_dict) 

該函數返回一個不可變對象,該對象的屬性以config參數名稱命名。

# suppose config file is something like: 
    # a = 1 
    # foo = bar 

    cfg = getConfig(...) 
    print cfg.a # prints 1 
    print cfg.foo # prints foo 
    print cfg.unknown # raises AttributeError 

我曾經使用這種方法來讀取標準ConfigParser實例的部分。