簡體   English   中英

類之外的變量范圍

[英]Variable scope outside of classes

我選擇的文本編輯器可以通過python插件進行擴展。 它需要我擴展類並覆蓋它的方法。 一般結構看起來類似於下面的代碼段。 請注意,功能簽名是固定的。

ftp_client應該由兩個類的實例共享。

ftp_client = None

class FtpFileCommand(sublime_plugin.TextCommand):
  def run(self, args):
    global ftp_client # does it reference the variable of the outer scope?
    self.ftp_client = ftplib.FTP('foo')
    # login and stuff

class FtpFileEventListener(sublime_plugin.EventListener):
  def run(self, args):
    global ftp_client # same for this
    self.ftp_client.quit() # 

這兩個類都應該有一個共同的變量。 分享變量的最佳做法是什么?

根據madjars回答編輯

FtpFileCommand.run調用FtpFileCommand.run ,實現ftp_client並且像魅力一樣工作。 FtpFileEventListener.run調用FtpFileEventListener.run ,可以完美地引用ftp_client ,但它仍然是None 使用global關鍵字,它是否將變量作為成員添加到self

是的,這正是global運作的方式。

在我看來,你做得對,因為它是在python標准庫的某些模塊中完成的( 例如fileinput )。

在這段代碼中:

global ftp_client # does it reference the variable of the outer scope?
self.ftp_client = ftplib.FTP('foo')

您將ftp_client聲明為全局變量。 這意味着它存在於模塊級別(例如,您的類所在的位置)。

第二行是錯誤的。 您想要分配給全局變量,而是設置一個同名的實例屬性。

它應該是:

global ftp_client
ftp_client = ftplib.FTP('foo')

但是,讓我提出一個不同的方法。 通常的做法是將這些東西放在類中,因為它由此類的所有實例共享。

class FtpFileCommand(sublime_plugin.TextCommand):
  ftp_client = None

  def run(self, args):
    FtpFileCommand.ftp_client = ftplib.FTP('foo')
    # login and stuff

請注意,該方法不使用self因此它也可能是一個類方法:

class FtpFileCommand(sublime_plugin.TextCommand):
  ftp_client = None

  @classmethod
  def run(cls, args):
    cls.ftp_client = ftplib.FTP('foo')
    # login and stuff

這樣,您將獲得該類作為第一個參數,您可以使用它來訪問FTP客戶端而不使用類名。

如果只有一個共享變量,那么全局是最簡單的解決方案。 但請注意,只有在賦值變量時才需要使用global聲明變量。 如果全局變量是一個對象,則可以調用其方法,修改其屬性等,而不必將其聲明為全局變量。

使用全局變量的替代方法是使用使用classmethods訪問的類屬性。 例如:

class FtpFile(object):
    _client = None

    @classmethod
    def client(cls):
        return cls._client

    @classmethod
    def setClient(cls, client):
        cls._client = client

class FtpFileCommand(FtpFile, sublime_plugin.TextCommand):
    def run(self, args):
        client = self.client()

class FtpFileEventListener(FtpFile, sublime_plugin.EventListener):
    def run(self, args):
        client = self.client()

氂牛...非常感謝你!

您將ftp_client聲明為全局變量。 這意味着它存在於模塊級別(例如,您的類所在的位置)。

我正在努力“正確地”編寫我的程序,我正在使用類和函數,並且無法調用任何變量。 我認識到全球化將使它在課堂之外可用。 當我讀到我認為...如果它存在於類之外,那么我需要從我正在導入該模塊的py腳本中檢索的變量將是:

module.variable

然后在該模塊中,我聲明了另一個全局變量來從主腳本中調用它......所以示例......

#Main Script main.py
import moduleA

print(moduleA.moduleA.variable)


#ModuleA code moduleA.py
import moduleB

class classA():

    def functionA():

      global moduleA_variable
      call.something.from.moduleB.classB.functionB()
      moduleA_variable = moduleB.moduleB_variable

ModuleB代碼moduleB.py

class classB():

     def functionB():

      global moduleB_variable
      moduleB_variable = retrieve.tacos()

我希望我的解釋也有助於某人。 我是python的初學者並且在這方面掙扎了一段時間。 如果不清楚......我有一些單獨的自定義模塊,由幾個不同的.py文件組成。 主要是調用moduleA而moduleA正在調用moduleB。 我不得不將鏈中的變量返回到主腳本。 我這樣做的關鍵是保持主要腳本在大多數情況下是干凈的,並且自己設置執行重復性任務而不必編寫垃圾頁面。 基本上嘗試重用函數而不是寫書。

你能為每個類添加一個構造函數,然后傳遞ftp_client作為參數嗎?

class FtpFileCommand(sublime_plugin.TextCommand):
    ...
    def __init__(self, ftp_client):
        self.ftp_client = ftp_client
    ...

class FtpFileEventListener(sublime_plugin.EventListener):
    ...
    def __init__(self, ftp_client):
        self.ftp_client = ftp_client
    ...

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM