为何使用NSLayoutConstraint.activate比逐个设置.isActive = true效率更高?
为什么NSLayoutConstraint.activate(_:)批量激活约束效率更高
核心原因是系统对批量操作做了多层级的优化,避免了大量重复计算和无效调度,具体逻辑如下:
1. 布局更新流程合并
单独设置isActive = true时,每激活一个约束,Auto Layout引擎都会立刻执行以下操作:
- 标记约束所属的视图层级为「布局脏状态」
- 调度一次布局重算请求到当前RunLoop
如果逐个激活10个约束,就会触发10次脏标记、10次调度请求,即使这些操作最终都在同一个RunLoop周期执行,中间的调度开销也会累积。
而批量激活时,系统会先把所有约束的变更全部收集完成后,只做1次脏状态标记、1次布局调度,直接省去了N-1次重复的调度开销。
2. 约束校验逻辑合并
每次约束激活时,系统都需要做两类校验:
- 约束冲突校验:检查已激活的约束是否存在优先级冲突
- 布局完整性校验:检查当前视图的约束是否足够确定位置和大小
逐个激活约束时,每加一个约束就会触发一次完整校验。比如你要给一个视图添加4个约束确定位置,逐个激活时前3次校验都会得到「约束不足、布局歧义」的结果,属于完全无效的计算。
批量激活时,系统会等所有约束都加载完成后,仅执行1次全局校验,直接跳过了中间过程的无效校验。
3. 视图挂载操作优化
每个约束激活时,都需要先找到两个关联视图的共同父视图,再把约束挂载到该父视图上。如果多个约束属于同一个视图层级,逐个激活时会重复执行「查找共同父视图」的遍历操作,批量激活时系统会对同层级的约束做合并处理,仅执行一次视图树遍历即可完成所有约束的挂载。
你提到的官方接口定义如下:
/* 便捷方法,可激活数组内的所有约束,效果与设置active=YES一致。该方法通常比逐个激活约束效率更高。 */ @available(iOS 8.0, *) open class func activate(_ constraints: [NSLayoutConstraint])
单独修改isActive本质是操作单个锚点的属性,对应定义:
@available(iOS 9.0, *) open var topAnchor: NSLayoutYAxisAnchor { get }
内容的提问来源于stack exchange,提问作者Gui Reis
相关产品推荐
相关产品推荐

