Unity构建时实例化非Mono类崩溃但编辑器正常问题求助
Unity构建版本实例化非MonoBehaviour类时无响应冻结问题
问题详情
- 在特定MonoBehaviour类内,使用
new()实例化非MonoBehaviour子类时,编辑器运行正常,但安卓/PC构建版本会无报错冻结,仅能输出实例化调用前的Debug.Log,后续日志全无。 - 改用反射
Activator.CreateInstance实例化同样无效,仅能输出"DEBUG 1"、"DEBUG 2"、"DEBUG 3",后续日志无输出。 - 已尝试切换Mono/IL2CPP后端、关闭代码剥离,未修改过程序集,问题仍存在。
代码示例
Awake方法代码
private void Awake() { Debug.Log("AWAKE CALL"); Debug.Log(new BluePrintItem.AICoreBlueprint().GetName()); Debug.Log("AWake after"); }
InitTierCraftedList方法代码
private void InitTierCraftedList() { Debug.Log("DEBUG 1"); List<Type> craftedItems = Assembly.GetAssembly(typeof(BluePrintItem)).GetTypes().ToList(). Where(Thetype => Thetype.IsClass && !Thetype.IsAbstract && Thetype.IsSubclassOf(typeof(BluePrintItem))).ToList(); Debug.Log("DEBUG 2"); Debug.Log(craftedItems.Count); foreach (var item in craftedItems) { Debug.Log("DEBUG 3"); BluePrintItem target = (BluePrintItem)Activator.CreateInstance(item); int highestTier = 0; Debug.Log("DEBUG 342"); foreach (var material in target.materialsList) { Debug.Log("DEBUG 4"); if (material.GetItemTier() > highestTier) { highestTier = material.GetItemTier(); Debug.Log("DEBUG 5"); } } Debug.Log("DEBUG 6"); switch (highestTier) { case 1: firstTierItems.Add(target.CraftedItemReference()); break; case 2: secondTierItems.Add(target.CraftedItemReference()); break; case 3: thirdTierItems.Add(target.CraftedItemReference()); break; case 4: forthTierItems.Add(target.CraftedItemReference()); break; default: Debug.LogWarning("CHECK HERE ASAP"); break; } } }
排查方向与解决方案
1. 检查子类构造函数逻辑
- 确认
BluePrintItem子类的构造函数中是否存在阻塞操作(如无限循环、死锁、等待未就绪资源),编辑器与构建环境的资源加载逻辑差异可能导致构建版卡住。 - 临时注释构造函数内非必要逻辑,逐步定位冻结触发点。
2. 字段初始化排查
- 若
materialsList是在构造函数外直接初始化(如public List<MaterialItem> materialsList = new List<MaterialItem>()),需确认初始化逻辑是否依赖编辑器专属API或未打包资源。 - 尝试将集合初始化移至构造函数内,避免静态初始化阶段的隐藏错误。
3. 反射类型过滤优化
- 反射获取的类型列表可能包含编辑器专用子类,这类类在构建版中无法正常实例化,可在
Where条件中添加过滤:&& !Thetype.Name.Contains("Editor")。 - 打印所有反射到的类型名称,确认是否存在异常类型:
foreach(var type in craftedItems) Debug.Log($"Found type: {type.FullName}");
4. 构建日志与崩溃信息捕获
- 勾选Build Settings中的"Show Build Log",查看构建时的详细警告或错误。
- PC构建可通过Windows事件查看器捕获崩溃信息;安卓构建通过Android Studio的LogCat过滤
Unity标签,查看冻结前的底层报错。
5. 强制引用避免代码优化
- 即使关闭代码剥离,未被显式引用的类型仍可能被优化,可在某个MonoBehaviour中添加强制引用:
public List<Type> KeepBlueprintTypes = new List<Type> { typeof(AICoreBlueprint), // 手动添加所有BluePrintItem子类 }; - 检查
BluePrintItem及其子类是否标记[Serializable],未标记可能导致构建版序列化异常。
内容的提问来源于stack exchange,提问作者Ali Ashrafi
相关产品推荐
相关产品推荐

