Python使用类和模块实现跨文件共享全局变量的一种方法

部署运行你感兴趣的模型镜像

翻译 Matlab 程序到 Python 时发现 Python 的 global 变量仅在当前文件内有效,因此需要找到一种方法实现跨文件的全局变量。

Python导入Model 时是导入同一个Model文件中的对象,因此可以用模块跨文件共享变量,故实现方法如下:

from typing import Any, Iterable, TypeVar


NameType = TypeVar('NameType', str, Iterable[str])


class GlobalVariable:
    def __init__(self) -> None:
        pass
    
    def all(self):
        attrs = [i for i in dir(self)]
        attr = []
        for i in range(len(attrs)):
            if len(attrs[i]) > 1:
                if '__' == attrs[i][:2]:
                    continue
            if attrs[i] in ['all', 'add', 'rm', 'get']:
                continue
            
            attr.append(attrs[i])
        return attr
        
    def add(self, name:NameType, value:Any):
        if isinstance(name, Iterable) \
            and (not isinstance(value, Iterable)):
            raise TypeError("value should be Iterable when name is Iterable")
        if type(name) is str:
            name = [name]
            value = [value]
            
        for n, v in zip(name, value):     
            exec('self.{}={}'.format(n, v))
        
    def rm(self, name:NameType):
        if type(name) is str:
            name = [name]
        for n in name:
            self.__delattr__(n)
    
    def get(self, name:NameType):
        if type(name) is str:
            return self.__getattribute__(name)
        else:
            attrs = []
            for n in name:
                attrs.append(self.__getattribute__(n))    
            return attrs
        

global  globalVariables

try: 
    tmp = globalVariables.all()
except NameError:
    globalVariables = GlobalVariable()
else:
    pass

将上述代码打包进 GlobalVariable.py 文件作为Python 模块,保存变量。

将变量打包进GlobalVariable类的 globalVariable实例中方便管理,同时增加 add(), rm(), all()方法方便对变量进行操作。

使用类属性管理变量,内存占用应该能比字典方式低。文件最后try-except语句自动实例化类,简化操作。

使用前仅需将GlobalVariable.py文件添加进可 import 的路径或用 sys.path.append 方法添加文件路径,然后

from GlobalVariable import globalVariables as gbv

添加变量:

# 添加一个名为 newVariable 的变量
# 方法一
gbv.newVariable = 199

# 方法二
gbv.add('newVariable', 199)


# 添加一系列变量
nameList = ['a', 'b', 'c']
valueList = [100, 200, 300]
gbv.add(nameList, valueList)

获取变量值:

# 方法一
gbv.varName

#方法二
gbv.get('varName')

nameList = ['name1', 'name2', 'name3']
gbv.get(nameList)

删除变量:

gbv.rm('variableName')

显示所有变量名:

gbv.all()

仓库见:

https://gitee.com/ddddavid-he/global-variable.git

您可能感兴趣的与本文相关的镜像

Python3.8

Python3.8

Conda
Python

Python 是一种高级、解释型、通用的编程语言,以其简洁易读的语法而闻名,适用于广泛的应用,包括Web开发、数据分析、人工智能和自动化脚本

<think>首先,用户的问题是关于Python中如何在不同文件之间使用全局变量。他们提供了几个引用,我需要从中提取关键点来构建答案。 关键引用总结: - 引用[1]:展示了从一个文件导入全局变量到另一个文件(main.py 从 config.py 导入 GLOBAL_VAR)。 - 引用[2]:描述了使用一个全局变量管理器模块(app.py),其中定义了全局变量初始化函数。 - 引用[3]:似引用[2],使用一个模块glob.py来管理全局变量,提供初始化、修改获取的函数。 - 引用[4]:讨论了导入模块时可能出现的名称冲突问题,如果导入路径不同可能导致多个实例。 - 引用[5]:提到一个问题,直接修改变量可能工作,但使用函数访问时可能出错,原因是初始化未执行。 用户的核心需求:查找Python全局变量跨文件使用方法。我需要提供一个清晰、结构化的回答,涵盖常见方法、注意事项最佳实践。 回答结构: 1. **介绍问题**:解释为什么需要跨文件使用全局变量。 2. **方法一:导入模块变量**(基于引用[1]):直接从另一个文件导入变量。 3. **方法二:使用全局变量管理模块**(基于引用[2][3]):创建一个模块来定义操作全局变量。 4. **方法三:使用单例模式或**:虽然不是直接引用,但这是常见实践。 5. **注意事项**:基于引用[4][5],讨论命名冲突、初始化问题并发风险。 6. **最佳实践建议**:推荐使用模块方法来封装状态。 7. **相关问题生成**:在末尾添加相关问题。 确保回答使用中文,符合系统指令: - 所有行内数学表达式用$...$格式(但这个问题没有数学内容,所以可能不需要)。 - 独立公式如果有的话用$$...$$(同样,可能不需要)。 - LaTeX语法正确(如果有数学,但这里没有)。 - 使用中文回答。 - 生成相关问题。 - 在引用的段落末尾添加引用标识。 引用部分: - 在回答中,当提到具体方法时,引用相关来源。例如,当讨论导入方法时,引用[^1];当讨论管理模块时,引用[^2][^3];注意事项引用[^4][^5]。 完整回答框架: 1. 开头:解释跨文件全局变量的概念。 2. 方法一:导入全局变量。 - 描述:在一个文件中定义变量,在另一个文件中导入。 - 示例代码(基于引用[1])。 - 引用[^1]。 3. 方法二:使用全局变量管理模块。 - 描述:定义一个模块来初始化管理变量。 - 示例代码(基于引用[2][3])。 - 引用[^2][^3]。 4. 方法三:使用或单例模式(扩展)。 - 描述:用封装全局状态。 - 示例代码(如果没有直接引用,可以简单描述)。 5. 注意事项: - 命名冲突(引用[^4])。 - 初始化问题(引用[^5])。 - 其他如线程安全。 6. 最佳实践:推荐使用模块方法。 7. 结尾:生成相关问题。 相关问题生成: - 基于内容,生成3-5个相关Python问题。 - 例如:"如何避免全局变量导入时的命名冲突?" 或 "在Python中如何安全地使用全局变量?" 最终输出格式: - 回答问题后,添加"§§相关问题§§"部分。 </think>### Python全局变量跨文件使用方法Python中,跨文件使用全局变量是常见的需求,例如在模块共享配置或状态数据。Python没有内置的“真正全局变量”,但可通过模块导入、全局管理器或单例模式实现。以下是基于您提供的引用总结的三种主要方法,我会逐步解释每种方法实现、优点注意事项。 #### 1. **直接导入模块变量(简单共享)** - **方法描述**:在一个文件中定义全局变量,在其他文件中通过`import`语句导入使用。这种方法简单直接,适用于小型项目。 - **示例代码**(基于引用[1]): - 定义全局变量的文件 `config.py`: ```python # config.py GLOBAL_VAR = "初始值" # 定义全局变量 ``` - 使用变量的文件 `main.py`: ```python # main.py from config import GLOBAL_VAR # 导入全局变量 def print_global_var(): print(GLOBAL_VAR) # 直接使用变量 if __name__ == "__main__": GLOBAL_VAR = "新值" # 可以修改,但仅影响当前文件的副本 print_global_var() # 输出: "新值" ``` - **优点**:实现简单,代码直观。 - **缺点**:导入的是变量的副本,而非引用。如果在不同文件中修改,不会自动同步(每个文件有自己的作用域)。需确保所有文件导入路径一致,避免命名冲突[^1]。 - **适用场景**:少量只读全局变量(如配置常量)。 #### 2. **使用全局变量管理模块(推荐方法)** - **方法描述**:创建一个专门的模块(如 `globals.py`)来定义全局变量,并提供初始化、修改获取的函数。所有文件导入该模块来操作共享状态。这种方法支持动态修改同步。 - **示例代码**(基于引用[2][3]): - 管理模块文件 `globals.py`: ```python # globals.py _global_var = None # 私有变量,通过函数访问 def init(): global _global_var _global_var = "初始值" # 初始化变量 def set_value(value): global _global_var _global_var = value # 修改变量 def get_value(): global _global_var return _global_var # 获取变量 ``` - 使用变量的文件 `app.py`: ```python # app.py import globals globals.init() # 必须先初始化 globals.set_value("修改后的值") print(globals.get_value()) # 输出: "修改后的值" ``` - 另一个文件 `user.py`: ```python # user.py import globals print(globals.get_value()) # 输出: "修改后的值",共享同一状态 ``` - **优点**: - 变量状态在所有文件中同步修改。 - 封装性好,避免直接修改变量导致的错误(如未初始化问题)。 - 支持复杂操作(如列表或对象修改)。 - **缺点**:需要显式调用初始化函数(否则可能报 `UnboundLocalError`,如引用[5]所述)[^2][^3][^5]。 - **最佳实践**:在程序入口(如 `main.py`)调用 `init()` 确保初始化。 #### 3. **使用或单例模式(面向对象方法)** - **方法描述**:用一个封装全局状态,通过单例模式确保所有文件访问同一实例。这种方法更面向对象,适合管理多个全局变量。 - **示例代码**(扩展引用[2]思想): - 管理文件 `config_manager.py`: ```python # config_manager.py class ConfigManager: _instance = None def __new__(cls): if cls._instance is None: cls._instance = super().__new__(cls) cls._instance.value = "初始值" # 初始化 return cls._instance def set_value(self, value): self.value = value def get_value(self): return self.value ``` - 使用变量的文件 `service.py`: ```python # service.py from config_manager import ConfigManager config = ConfigManager() config.set_value("新值") ``` - 另一个文件 `client.py`: ```python # client.py from config_manager import ConfigManager config = ConfigManager() print(config.get_value()) # 输出: "新值" ``` - **优点**:状态严格共享,支持扩展(如添加日志或验证)。 - **缺点**:代码稍复杂,需确保所有文件导入同一实例。 - **适用场景**:大型项目,需要高可维护性。 #### 关键注意事项 1. **导入路径问题**(基于引用[4]):如果不同文件使用不同路径导入同一模块(如 `import test_dic.test2` vs `import test2`),Python会创建多个模块实例,导致变量不同步。解决方法:统一使用绝对路径导入或设置 `sys.path`[^4]。 2. **初始化问题**(基于引用[5]):全局变量必须在访问前初始化。例如,直接修改变量可能工作,但如果跳过初始化步骤(如未调用 `init()`),函数访问会报错 `UnboundLocalError`。建议在模块加载时自动初始化[^5]。 3. **并发风险**:多线程或多进程环境中,全局变量修改可能导致竞态条件。如果共享状态,建议添加锁机制或使用线程安全数据结构。 4. **避免过度使用**:全局变量增加耦合度,优先考虑传递参数或依赖注入。 #### 推荐最佳实践 - **小型项目**:使用方法一(导入模块变量),但仅用于只读变量。 - **大多数场景**:使用方法二(全局管理模块),它平衡了简单性可靠性。确保在程序启动时调用初始化函数。 - **复杂系统**:使用方法三(单例),结合型注解增强可读性。 通过以上方法,您可以安全地在不同文件间共享全局变量。如果需要更多代码示例或调试帮助,请提供具体场景!
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值