You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用is关键字判断对象是否为任意泛型UIHostingController?

检测任意泛型参数的UIHostingController实例

问题核心

Swift中使用is关键字判断泛型类时必须指定具体泛型参数,但UIHostingController的Content类型可能是任意视图(比如ModifiedContent、自定义View等),指定固定类型(如UIHostingController<AnyView>)会因为类型不匹配导致判断失败。

解决方案

方法1:利用Objective-C运行时(最简便)

UIHostingController继承自UIViewController,而Objective-C运行时不区分Swift泛型类的泛型参数,直接用isKind(of:)即可匹配任意Content类型的实例:

let vc = window.rootViewController?.children.last { 
    $0.isKind(of: UIHostingController.self) 
}

方法2:纯Swift协议擦除(最优雅)

定义一个空协议,让所有UIHostingController的泛型实例自动遵守,通过协议实现类型擦除:

// 定义空协议
protocol AnyUIHostingController {}
// 让所有UIHostingController实例遵守协议
extension UIHostingController: AnyUIHostingController {}

// 使用方式
let vc = window.rootViewController?.children.last { $0 is AnyUIHostingController }

这种方法完全基于Swift类型系统,不依赖外部运行时,类型安全且代码简洁。

方法3:遍历类继承链(纯Swift无依赖)

通过遍历对象的类继承链,检查类名特征来判断:

import ObjectiveC.runtime

func isAnyUIHostingController(_ vc: UIViewController) -> Bool {
    var currentType: Any.Type = type(of: vc)
    while let baseClass = currentType as? AnyClass {
        let className = String(describing: baseClass)
        if className.hasPrefix("UIHostingController<") {
            return true
        }
        currentType = class_getSuperclass(baseClass)!
    }
    return false
}

// 使用方式
let vc = window.rootViewController?.children.last { isAnyUIHostingController($0) }

这种方法不依赖Objective-C运行时的动态判断,但需要依赖类名格式,优雅度稍差。

内容的提问来源于stack exchange,提问作者mckeed

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 19:12:11