假设我们在一个Python项目中,有以下两个数据文件:
data/character_data.py
CHARACTER_A = {
1: {"level": 1, "name": "Ann", "skill_level" : 1},
2: {"level": 2, "name": "Tom", "skill_level" : 1}
}
CHARACTER_B = {
1: {"level": 1, "name": "Kai", "skill_level" : 1},
2: {"level": 2, "name": "Mel", "skill_level" : 1}
}
在我们的主程序main.py中,我们可以通过以下方式访问这些数据:
from data import character_data as character_data
print(character_data.CHARACTER_A[1]["name"])
# 输出: Ann
print(character_data.CHARACTER_B[2]["name"])
# 输出: Mel
但问题是,如果我们想动态地访问这些数据,比如根据输入的变量来确定要访问哪个字典和哪个键,该怎么办?
例如,我们有如下代码:
from data import character_data as character_data
character_type = "CHARACTER_A"
character_id = 1
print(character_data.character_type[character_id]["name"])
# 输出: AttributeError: 'module' object has no attribute 'character_type'
显然,这种方式会报错,因为我们不能直接通过模块名来访问字典。
2 解决方案
方法一:使用locals()
我们可以使用locals()
函数来动态地访问变量。locals()
函数返回当前作用域(或执行代码的上下文中)的所有局部变量。
例如,我们可以在main.py
中使用如下代码:
from data import character_data as character_data
character_type = "CHARACTER_A"
character_id = 1
print(locals()[character_type][character_id]["name"])
# 输出: Ann
这种方法可以实现动态访问字典,但它并不是非常优雅。
方法二:使用getattr()
我们可以使用getattr()
函数来动态地访问属性或方法。getattr()
函数接受两个参数:对象和属性名,并返回指定对象的指定属性值。
例如,我们可以在main.py
中使用如下代码:
from data import character_data as character_data
character_type = "CHARACTER_A"
character_id = 1
print(getattr(character_data, character_type)[character_id]["name"])
# 输出: Ann
这种方法比使用locals()
更简洁和优雅。
方法三:使用面向对象编程
我们也可以使用面向对象编程来解决这个问题。我们可以创建一个Character
类,并使用实例化对象来存储角色数据。
例如,我们可以如下定义Character
类:
class Character(object):
def __init__(self, character_type, character_id, name, level, skill_level):
self.character_type = character_type
self.character_id = character_id
self.name = name
self.level = level
self.skill_level = skill_level
然后,我们可以如下实例化Character
对象:
character_a1 = Character("CHARACTER_A", 1, "Ann", 1, 1)
character_a2 = Character("CHARACTER_A", 2, "Tom", 2, 1)
character_b1 = Character("CHARACTER_B", 1, "Kai", 1, 1)
character_b2 = Character("CHARACTER_B", 2, "Mel", 2, 1)
最后,我们可以使用如下代码来动态访问角色数据:
character_type = "CHARACTER_A"
character_id = 1
character = eval(character_type + str(character_id))
print(character.name)
# 输出: Ann
这种方法更灵活和可扩展,因为它允许我们存储更多角色数据,并且我们可以很容易地添加新的角色。