2012-01-31 100 views
0

我在python中創建了一個包。在init文件中,我放置了一個必須在此包的所有模塊中可用的變量。python包結構和全局變量

例子:

# main script  
from _Framework.STB import DB 
DB.environment = 'lab' 
channel = DB.Channels.ChannelStatic.getChannelByNumber(416) 
... 

# Channels.py module in the package 
from _Framework.DB.__init__ import cursor 
from _Framework.DB.__init__ import environment 
from time import * 
... 

的問題是,要

from _Framework.DB.__init__ import xy 

everdy通話將覆蓋我的 「全局」 變量

我該如何解決?

感謝

編輯:

init.py:

all = [ 'Events', 'Channels', 'Genres', 'Subgenres','EPGSections'] 
try: 
    conn = MySQLdb.connect(host,user,passwd,db) 
    cursor = conn.cursor(MySQLdb.cursors.DictCursor) 
except: 
    cursor = None 
    environment = 'live' 

我導入DB包,我設置了 「環境」 變量,但在通道模塊是進口的,我想,它會重新調用init.py並重新執行其代碼,以便覆蓋「environment」。我正在尋找一種乾淨的方式來共享相同包裝模塊之間的變量

+0

我真的不明白你問題的問題。你可以發佈__init__.py代碼和來自模塊的更多代碼,其中導入「覆蓋你的'全局'變量',說明究竟是什麼被覆蓋以及由誰? – Bogdan 2012-01-31 12:32:47

+0

######################## __init__.py __all__ = ['Events','Channels','Genres','Subgenres',' EPGSections'] 嘗試: 康恩= MySQLdb.connect(主機,用戶,passwd中,分貝) 光標= conn.cursor(MySQLdb.cursors.DictCursor) 除外: 光標=無 環境= '活' 在my_script.py中我導入了數據包包,並設置了「環境」變量,但是當導入Channels模塊時,我認爲它會對__init__.py進行新的調用並重新執行其代碼,以便「環境」被覆蓋。 我正在尋找一個乾淨的方式來共享相同包的模塊之間的變量 – 2012-01-31 13:49:13

+0

你知道你可以編輯這個問題嗎? – 2012-01-31 14:40:02

回答

0

我仍然不確定,但如果我理解正確。你應該只使用編輯你的問題,並張貼正確格式化代碼:在Channels.py

__init__.py: 

all = [ 'Events', 'Channels', 'Genres', 'Subgenres','EPGSections'] 
try: 
    conn = MySQLdb.connect(host,user,passwd,db) 
    cursor = conn.cursor(MySQLdb.cursors.DictCursor) 
except: 
    cursor = None 
    environment = 'live 

現在要更改_Framework.DB.__init__.cursor_Framework.DB.__init__.environment這種變化應該可以看出各地你的程序?

如果這是你想你應該知道,當你在導入做什麼:

from _Framework.DB.__init__ import cursor 
from _Framework.DB.__init__ import environment 

什麼情況是,你會得到兩個變量光標和環境,你Channels.py模塊命名空間和任何改變你do只會在該模塊中可見。如果你想達到你的結果試試這個:

import _Framework.DB 

_Framework.DB.cursor = new_cursor 
_Framework.DB.environment = new_environment 

這樣你實際上改變模塊變量。現在,在你的程序的其餘部分,當你想看到的變化生效,你既可以:

  1. ACCES在你改變了他們以同樣的方式可變因素:

    進口_Framework.DB

    _Framework.DB.cursor  #changes made in other module will have effect 
    _Framework.DB.environment #changes made in other module will have effect 
    
  2. 像你這樣的導入,但確保你想做的改變是在你做任何導入之前完成的。

    至於第二種情況的反面例子:

    #module Vars 
    a = 1 
    
    -------------------------- 
    
    #module Do_change 
    import Vars 
    Vars.a = 2 
    
    -------------------------- 
    
    #module A 
    from Vars import a 
    
    
    -------------------------- 
    
    #module B 
    from Vars import a 
    
    -------------------------- 
    
    #some random module 
    import A 
    import Do_change 
    import B 
    

現在,如果你是在進口這樣才能在導入它將會在與瓦爾值命名空間創建一個變量。一個。 Do_change將相應地編輯變量,但A將不知道這一點。B但是誰進口後,將看到正確的Vars.a = 2.

這就是爲什麼我真的推薦第一個選項,因爲它是在我看來是正確的方法。

+0

謝謝你的答案,我很抱歉我格式不好的答案,但stackoverflow不允許我回答一個問題,發佈後超過8小時後。無論如何,我解決了通過創建另一個模塊安裝程序並將其__init__中的所有代碼移動。它現在有效。我會盡力實施你的解決方案,如果效果更好的話。再一次非常感謝你! – 2012-01-31 15:07:45

2

從模塊__init__導入像

from package.__init__ import X 

運行每次模塊代碼。這就是爲什麼你的變量被覆蓋。這是因爲在sys.modules__init__模塊正在被添加兩次(使用不同的名稱)。首先,在導入時將其作爲包的名稱,然後在明確導入時作爲package.__init__。由於源被加載兩次,代碼被執行兩次。

但是你不需要做這樣,你只需要做:

from _Framework.DB import cursor 
from _Framework.DB import environment 

那麼你的代碼將只運行一次。

+0

+1確實,從包的'__init__'導入是一個糟糕的python編程習慣。 – martineau 2012-01-31 18:37:15