Python字典动态读写、实时重计算及特定区域保护问题求助
解决方案:区分实时计算怪物与可修改特殊区域
核心思路是将需要实时计算属性的怪物定义为生成函数,在加载条目时动态生成最新属性;而**"Replicated Replicator Replica"这类特殊区域直接存储实际字典**,保留外部修改的能力。
重构后的代码示例
import random class stat_tracker: stat_class_hp = 1000 class monsters: all_monsters = { "Sewer": { # 用lambda作为生成函数,加载时动态计算属性 1: lambda: {"Name": "The Beast", "HP": 4500}, }, "Tourney 1": { # 依赖stat_tracker的属性实时计算 1: lambda: {"Name": "Simon Sais", "HP": stat_tracker.stat_class_hp * 2}, }, "Replicated Replicator Replica": { # 特殊区域直接存储实际字典,支持外部修改 1: {"NUL"} }, } def combat_encounter_roller(current_zone): zone_monsters = monsters.all_monsters.get(current_zone) if not zone_monsters: return None monster_entry = zone_monsters[1] # 区分处理:如果是生成函数则执行获取最新属性,否则直接返回存储的对象 if callable(monster_entry): return monster_entry() else: return monster_entry class current_zone: name = "" class current_monster: whole_monster = {} monster_name = "Test" monster_hp = 0 def initialize_monster_stats(zone): monster = combat_encounter_roller(zone) current_monster.whole_monster = monster if "Name" in monster: current_monster.monster_name = monster["Name"] if "HP" in monster: current_monster.monster_hp = monster["HP"] def use_battle_item(): effect_name = "Replicator Replicate" if effect_name == "Replicator Replicate": # 直接修改特殊区域的存储对象,修改会被保留 monsters.all_monsters["Replicated Replicator Replica"][1] = current_monster.whole_monster.copy() print("You quickly scanned the monster and made a copy!") def combat_prompt(zone): current_zone.name = zone initialize_monster_stats(zone) use_battle_item() # 测试逻辑 print(monsters.all_monsters["Replicated Replicator Replica"][1]) combat_prompt("Tourney 1") stat_tracker.stat_class_hp *= 2 combat_prompt("Tourney 1") stat_tracker.stat_class_hp *= 2 print(stat_tracker.stat_class_hp * 2, current_monster.monster_hp, "These two values should be equal") print(monsters.all_monsters["Replicated Replicator Replica"][1])
关键细节说明
- 实时计算实现:普通怪物用
lambda生成函数,每次调用combat_encounter_roller时都会执行函数,基于最新的stat_tracker值生成属性,避免了定义时一次性计算的问题。 - 特殊区域保留可修改性:特殊区域直接存储字典对象,获取时直接返回原对象,外部修改(如
use_battle_item中的操作)会直接作用于存储的字典,不会被后续加载操作覆盖。 - 数据隔离:普通怪物每次生成新的字典实例,不会相互干扰;特殊区域的修改会被持久化存储,直到被再次修改。
为什么之前的方案有问题
- 直接存储计算值:原代码中
Tourney 1的HP是定义时计算的,只会执行一次,后续stat_tracker变化不会同步更新。 - 用方法但未区分区域:如果所有怪物都用方法生成,特殊区域的修改会在下次加载时被方法重置,无法保留外部修改;而区分处理后,特殊区域的存储对象独立于计算逻辑,修改不会被覆盖。
内容的提问来源于stack exchange,提问作者HyperCShell
相关产品推荐
相关产品推荐

