如何重构Unity C#中判断多个GameObject激活状态的冗长if条件
重构优化方案
原冗长连续或判断的核心问题是硬编码索引分散在条件块中,后续维护增删检测项极易出错,且缺少边界、空值校验容易触发运行时异常,可按以下方式重构:
方案1:局部快速优化(单处使用逻辑)
引入LINQ的Any方法实现短路判断(和原||运算逻辑完全一致,匹配到第一个符合条件的对象就终止遍历,无额外性能开销),将所有待检测的索引集中维护:
// 首先引入LINQ命名空间 using System.Linq; // 业务逻辑处 // 所有需要检测的武器索引集中配置,增删检测项仅需修改此处数组 int[] needCheckIndexes = {1,2,3,4,5,8,10,12,13,14,15,16,17}; if (needCheckIndexes.Any(index => // 增加索引越界判断、空对象判断,避免运行时报错 index < Customanger.singleton.weapon.Count && Customanger.singleton.weapon[index] != null && Customanger.singleton.weapon[index].activeSelf)) { dosomething(); }
该写法的优势:
- 索引集中管理,不会出现漏写
||、写错索引数值的低级错误 - 自带异常防护,避免列表长度不足、对应索引位置武器对象为空时触发崩溃
- 执行逻辑和原代码100%一致,不存在行为差异
方案2:封装复用(多处调用该逻辑时推荐)
将判断逻辑和待检测索引封装到Customanger类内部,支持可视化配置,全局复用:
using System.Linq; using UnityEngine; using System.Collections.Generic; public class Customanger : MonoBehaviour { public List<GameObject> weapon; public static Customanger singleton; // 可直接在Unity Inspector面板配置需要检测的武器索引,无需修改代码 public int[] checkActiveWeaponIndexes = {1,2,3,4,5,8,10,12,13,14,15,16,17}; /// <summary> /// 是否存在任意一个目标武器处于激活状态 /// </summary> public bool AnyTargetWeaponActive => checkActiveWeaponIndexes.Any(index => index < weapon.Count && weapon[index] != null && weapon[index].activeSelf); private void Awake() => singleton = this; }
原判断逻辑可简化为一行,全局任意位置调用都不需要重复写索引列表:
if (Customanger.singleton.AnyTargetWeaponActive) { dosomething(); }
该方案额外优势:
- 支持Inspector可视化配置,非程序人员也可调整检测规则
- 全局逻辑统一,不会出现不同位置检测的武器列表不一致的bug
方案3:无LINQ兼容写法
如果项目有特殊要求禁止使用LINQ,可通过普通循环实现相同短路逻辑:
int[] needCheckIndexes = {1,2,3,4,5,8,10,12,13,14,15,16,17}; bool existActiveWeapon = false; foreach (int index in needCheckIndexes) { if (index >= Customanger.singleton.weapon.Count) continue; GameObject targetWeapon = Customanger.singleton.weapon[index]; if (targetWeapon != null && targetWeapon.activeSelf) { existActiveWeapon = true; break; // 找到符合条件的对象立刻终止遍历,和原||逻辑一致 } } if (existActiveWeapon) { dosomething(); }
内容的提问来源于stack exchange,提问作者fatdrogen
相关产品推荐
相关产品推荐

