彻底搞懂 Swift 的 Any、AnyObject、any

一张速查表先拎清

名称 具体类型 能容纳 典型场景 Swift 版本
Any 顶层类型(具体类型) 任意值(含函数、元组、struct、class) 与旧 API 交互、极少数极端动态场景 1.0+
AnyObject 协议(仅类/actor 遵循) 引用类型(class / actor) 弱引用容器、协议限制为引用语义 1.0+
any existential 关键字 任意协议(含关联类型) 声明"存在某个协议实现" 5.7+

Any:万能口袋,但请少用

swift 复制代码
let bag: [Any] = [
    "Jack",                // String
    55,                    // Int
    { () -> Void in },     // 闭包
    (44.9, 0)              // 元组
]

问题:类型安全被"蒸发"

swift 复制代码
struct StringValidator {
    func validate(_ value: Any) -> Bool {
        guard let str = value as? String else {
            fatalError("只接受 String")   // 运行时爆炸
        }
        return !str.isEmpty
    }
}

更安全的替代

  • 协议约束(推荐 1)
swift 复制代码
protocol Validator {
    associatedtype Value
    func validate(_ value: Value) -> Bool
}

struct StringValidator: Validator {
    typealias Value = String
    func validate(_ value: String) -> Bool { !value.isEmpty }
}
  • 泛型(推荐 2)
swift 复制代码
struct AnyValidator<T>: Validator {
    typealias Value = T
    func validate(_ value: T) -> Bool {
        if let str = value as? String { return !str.isEmpty }
        if let int = value as? Int { return int > 0 }
        return false
    }
}

总结:能用协议/泛型就别用 Any。

AnyObject:只拥抱引用类型

  • 只有 classactor 隐式遵循。
  • 协议限制为"必须是引用类型"。
swift 复制代码
protocol Cache: AnyObject {
    func clear()
}

class MemoryCache: Cache {
    func clear() { print("内存缓存清空") }
}

struct DiskCache: Cache { /* ❌ struct 无法遵守 AnyObject 协议 */ }

func perform(_ c: AnyObject) { /* 只接受引用类型 */ }

与 actor 搭配

swift 复制代码
actor Counter {
    private var value = 0
    nonisolated func description() -> String { "CounterActor" }
}

let obj: AnyObject = Counter()

注意:nonisolated 让 actor 方法同步调用,避免 await。

any:existential 关键字(Swift 5.7+)

  • 用于 带关联类型的协议 或 需要运行时多态 时。
  • 不是类型,而是标记:"这是一个盒子,里面装着某个具体实现"。

带关联类型的协议

swift 复制代码
protocol AppleDevice {
    associatedtype Chip
    var chip: Chip { get }
}

class ModernMacBook: AppleDevice {
    typealias Chip = String
    let chip = "M3"
}

class OldMacBook: AppleDevice {
    typealias Chip = Int
    let chip = 42
}

// ✅ 正确:用 any 声明 existential
let devices: [any AppleDevice] = [ModernMacBook(), OldMacBook()]

// ❌ 错误:不能直接用协议名
// 使用协议类型,前面默认使用any修饰。目前会报警告,但后续会报错。需要明确写上any
// let wrong: [AppleDevice] = [ModernMacBook(), OldMacBook()]

与 some 的区别

关键字 含义 何时使用
some opaque type(编译期已知具体类型) 返回值隐藏实现细节
any existential(运行时才知道具体类型) 参数、集合元素
swift 复制代码
func opaque() -> some AppleDevice { ModernMacBook() }  // 编译期确定
func existential(_ d: any AppleDevice) { ... }         // 运行时多态

实战:弱引用容器场景

用 AnyObject 存储 delegate

swift 复制代码
final class MulticastDelegate {
    private var delegates = NSHashTable<AnyObject>.weakObjects()

    func add<T: AnyObject>(_ delegate: T) {
        delegates.add(delegate)
    }
}

用 any 擦除带关联类型的协议

swift 复制代码
protocol EventHandler {
    associatedtype Event
    func handle(_ event: Event)
}

struct AnyHandler<Event>: EventHandler {
    private let _handle: (Event) -> Void
    init<H: EventHandler>(_ handler: H) where H.Event == Event {
        _handle = handler.handle
    }
    func handle(_ event: Event) { _handle(event) }
}

一句话总结

  • Any ≈ 远古时代的 id,能装万物,但类型信息全丢。
  • AnyObject ≈ "必须是引用类型"的协议约束,常用于弱引用容器。
  • any ≈ Swift 5.7 的新关键字,解决"带关联类型协议"的泛型多态问题。

开发口诀:能用具体类型 > 泛型 > 协议 > any > AnyObject > Any

按此优先级,你将获得类型安全、性能与可读性的三重保障。

相关推荐
初级代码游戏1 天前
iOS开发 SwiftUI 14:ScrollView 滚动视图
ios·swiftui·swift
初级代码游戏1 天前
iOS开发 SwitftUI 13:提示、弹窗、上下文菜单
ios·swiftui·swift·弹窗·消息框
zhyongrui1 天前
托盘删除手势与引导体验修复:滚动冲突、画布消失动画、气泡边框
ios·性能优化·swiftui·swift
zhangfeng11331 天前
CSDN星图 支持大模型微调 trl axolotl Unsloth 趋动云 LLaMA-Factory Unsloth ms-swift 模型训练
服务器·人工智能·swift
zhyongrui2 天前
SnipTrip 发热优化实战:从 60Hz 到 30Hz 的性能之旅
ios·swiftui·swift
大熊猫侯佩3 天前
Neo-Cupertino 档案:撕开 Actor 的伪装,回归 Non-Sendable 的暴力美学
swift·observable·actor·concurrency·sendable·nonsendable·data race
2501_915921434 天前
在没有源码的前提下,怎么对 Swift 做混淆,IPA 混淆
android·开发语言·ios·小程序·uni-app·iphone·swift
00后程序员张5 天前
对比 Ipa Guard 与 Swift Shield 在 iOS 应用安全处理中的使用差异
android·开发语言·ios·小程序·uni-app·iphone·swift
大熊猫侯佩5 天前
星际穿越:SwiftUI 如何让 ForEach 遍历异构数据(Heterogeneous)集合
swiftui·swift·遍历·foreach·any·异构集合·heterogeneous
hjs_deeplearning5 天前
认知篇#15:ms-swift微调中gradient_accumulation_steps和warmup_ratio等参数的意义与设置
开发语言·人工智能·机器学习·swift·vlm