簡體   English   中英

從另一個模塊看不到對 static class 變量的更改

[英]Changes to static class variable are not visible from another module

我正在為一些 REST ZDB974238714CA8DE63ZA7CED1 To make it easier to manipulate the state of the objects I get from the API, I want to store a static reference to my API client instance. 假設我有一個文件user.py

class User:
    _client: Client = None

因此,當客戶端第一次成功通過身份驗證時,我更新了引用:

class Client:
    def authenticate(self):
        ...
        User._client = self

這發生在我的client.py文件中。 現在我可以從client.py中聲明的任何 function 成功訪問User._client ,但是當我從另一個模塊嘗試相同的事情時, User._client仍然是None

假設這是我的文件夾結構

└── my_api_client
    ├── __init__.py
    ├── client.py
    ├── search.py
    └── user.py

然后,當我從search.py 中的 function 調用User._client時,我得到None而不是對當前客戶端實例的引用。

我在創建一個演示此問題的最小工作示例時遇到了麻煩,所以也許我只是在導入時弄亂了一些東西。 如果我從另一個模塊導入 class 並且如果對 class 的 static 屬性的引用在所有模塊之間共享,我認為如果我更好地理解會發生什么,這將真的很有幫助。 如果確實如此,我做錯了什么?

我試圖重現你的問題,但不能。

# user.py

print("defining class User")


class User:
    _client = None  # removed type annotation here to prevent circular import


print("right now, User._client is " + repr(User._client))
# client.py

import user


class Client:
    def authenticate(self):
        user.User._client = self


print("instantiating a Client")
client = Client()
print("before athenticating, the User._client is " + repr(so70744003_user.User._client))
client.authenticate()
print("before athenticating, the User._client is " + repr(so70744003_user.User._client))

並運行文件client.py

defining class User
right now, User._client is None
instantiating a Client
before athenticating, the User._client is None
before athenticating, the User._client is <__main__.Client object at 0x7fc1816a9b20>

我可以給你詳細說明發生了什么:

  • Python 獲得了文件client.py所以開始運行文件中的代碼
  • 它以import user開頭,因此 Python 將搜索user模塊並加載它
    • Python 沒有內置user模塊,因此它會在其sys.path目錄中搜索它,並找到匹配的文件
    • Python starts running the user.py file, which defines a User class, so it instantiates a class instance for it (with a static member _client set to None ), and binds it to the User name in the current module
    • 然后它打印出User的 static 成員_client確實是None
    • 運行完user.py文件后,Python 繼續運行client.py文件
  • 導入成功,所以 Python 有一個module object 並將其綁定到當前模塊 scope ( client )中的user
  • 繼續運行文件,遇到 class 定義(定義了一個方法),它被綁定到當前模塊中的Client名稱
  • 然后它實例化一個Client並將其綁定到當前模塊中的client名稱(也命名為client
  • 然后它調用authenticate ,它將user (指向從user.py ._client .User類中的 static 變量)設置為self
  • 最后它打印出 static 變量 new value 實際上是Client的一個實例

在您的問題評論中,建議使用global變量。 它不會改變任何事情,因為您的User class 本質上已經是singleton (只有一個聲明),您只是碰巧訪問了它的一個字段。 單身人士的字段也可以視為 singleton 值。

我不知道你的實現有什么問題,你沒有給我們足夠的東西來找到錯誤。 如果您想找到它,我建議嘗試將其簡化為Minimal Reproducible Example 通常在這個過程中,你會自己找到解決方案。

我擔心這可能是由相互導入引起的,因此變量的 state 取決於項目每個文件中導入語句的順序。 這是嘗試打破周期或在它們周圍小心的理由。

暫無
暫無

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

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