使用count 还是isEmpty检查集合是否为空?

文章比较了Swift中使用count和isEmpty检查集合是否为空的效率,指出isEmpty在时间复杂度上优于count,尤其是在处理String等非RandomAccessCollection类型时。建议优先使用isEmpty以提高代码效率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

使用count 还是isEmpty检查集合是否为空?

在Swift中,基本上有两种主要方法来检查给定的集合是否为空。我们可以检查集合的count是否等于0,也可以使用专用的isEmpty属性。

起初,两者的行为方式似乎完全相同。事实上,将isEmpty想象为使用count检查实现是完全合理的——像这样:

extension Collection {
    var isEmpty: Bool { count == 0 }
}

然而,实际上,事实证明,标准库对isEmpty的默认实现看起来像这样:

extension Collection {
    var isEmpty: Bool { startIndex == endIndex }
}

然而,某些具体的集合类型随后提供了isEmpty的自定义实现,以更适合其特定的工作方式——这是事情变得有趣的地方,如果看看Set如何实现该属性,那么会发现它确实使用了上面想象的完全相同的count检查:

extension Set {
    var isEmpty: Bool { count == 0 }
}

怎么回事呢? 为了回答这个问题,让我们看看count属性的官方文件,其中包括以下句子:

复杂性:O(1)如果集合符合RandomAccessCollection;否则,O(n),其中n是集合的长度。

因此,事实证明,简单地访问某些集合上的count属性会导致一个在时间复杂度方面为O(n)的操作。 换句话说,需要遍历一遍集合的所有元素。

这种集合的一个例子是String,几乎每个Swift程序都使用。在Swift中,字符串的count是指字符串包含的人类可读字符的数量,这些字符实际上存储为UTF-8代码点。这两种格式不一定具有相同的长度,事实上,确定字符串的确切字符数确实需要遍历所有UTF-8内容(这是一个O(n)操作),以计算其startIndexendIndex之间的确切距离:

extension String {
    var count: Int {
        distance(from: startIndex, to: endIndex)
    }
}

这就是为什么Collection协议的isEmpty默认实现是检查startIndexendIndex属性是否相等,而不是使用count,因为访问这两个索引属性不需要执行任何实际计算。

那么,总而言之——使用isEmptycount == 0是等价的吗?有时是的(例如在处理Set时),但有时(如在String的情况下)不是, 后者存在令人难以置信的浪费——因为需要遍历整个集合,才可以检查该计数是否等于0

我的建议:始终使用isEmpty检查集合是否为空。它读起来更好,更不言自明,而且总是超级快。仅当对集合中元素的实际数量感兴趣时,才使用count计数。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值