如何在不将Tile类改为抽象类的前提下移除状态判断的if-else分支
如何在不将Tile类改为抽象类的前提下移除状态判断的if-else分支
这问题我之前也遇到过!你想要的其实是状态模式的一种灵活实现,既能把状态和对应的行为绑定,又不用改动Tile类的基础结构(不用改成抽象类)。下面给你两种实用的方案:
方案一:基于接口的状态行为封装(适合逻辑复杂的场景)
这种方式把每个状态对应的逻辑封装成独立的类,代码结构清晰,便于后续扩展和维护。
首先定义一个统一的状态行为接口:
public interface ITileStateBehavior { void OnStep(); }
然后为每个State枚举值创建对应的行为实现类:
// 正常状态的行为逻辑 public class NormalTileBehavior : ITileStateBehavior { public void OnStep() { // 原来State.normal对应的逻辑代码 } } // 空状态的行为逻辑 public class EmptyTileBehavior : ITileStateBehavior { public void OnStep() { // 原来State.empty对应的逻辑代码 } } // 危险状态的行为逻辑 public class HazardTileBehavior : ITileStateBehavior { public void OnStep() { // 原来State.hazard对应的逻辑代码 } }
最后修改Tile类,维护一个状态到行为的映射表,移除if-else分支:
public class Tile { private State _state; // 存储状态与对应行为的映射关系 private readonly Dictionary<State, ITileStateBehavior> _stateBehaviors; public Tile() { // 初始化映射表 _stateBehaviors = new Dictionary<State, ITileStateBehavior> { { State.normal, new NormalTileBehavior() }, { State.empty, new EmptyTileBehavior() }, { State.hazard, new HazardTileBehavior() } }; } public void OnStep() { // 根据当前状态直接获取对应的行为并执行 if (_stateBehaviors.TryGetValue(_state, out var behavior)) { behavior.OnStep(); } // 可选:处理未定义的状态(比如抛出异常或执行默认逻辑) else { // throw new InvalidOperationException($"Unsupported state: {_state}"); } } // 提供状态的访问器,方便外部修改Tile的状态 public State State { get => _state; set => _state = value; } }
方案二:基于委托的轻量实现(适合逻辑简单的场景)
如果每个状态的逻辑代码不多,不想创建大量的行为类,可以用Action委托来简化实现,代码更紧凑:
public class Tile { private State _state; // 存储状态与对应逻辑的委托映射 private readonly Dictionary<State, Action> _stateActions; public Tile() { _stateActions = new Dictionary<State, Action> { { State.normal, () => { /* 这里写State.normal对应的逻辑 */ } }, { State.empty, () => { /* 这里写State.empty对应的逻辑 */ } }, { State.hazard, () => { /* 这里写State.hazard对应的逻辑 */ } } }; } public void OnStep() { if (_stateActions.TryGetValue(_state, out var action)) { action.Invoke(); } } public State State { get => _state; set => _state = value; } }
方案优势说明
两种方案都完全符合你的需求:
- 不需要将
Tile类改为抽象类,保持原有类结构的完整性 - 实现了状态与行为的绑定,逻辑不再分散在if-else分支里
- 后续新增状态时,只需要添加对应的行为类/委托逻辑,更新映射表即可,无需修改
OnStep方法,完全符合开闭原则
备注:内容来源于stack exchange,提问作者hikariakio
相关产品推荐
相关产品推荐

