遍历数组的最后一个索引以外的所有索引

Posted

技术标签:

【中文标题】遍历数组的最后一个索引以外的所有索引【英文标题】:Iterating through all but the last index of an array 【发布时间】:2017-04-19 07:15:58 【问题描述】:

我知道在 Swift 3 中,典型的 C 风格 for 循环发生了一些变化。我一直在解决它,但在很多情况下,我似乎比以前编写了更多的代码。也许有人可以引导我朝着正确的方向前进,因为这就是我想要的:

let names : [String] = ["Jim", "Jenny", "Earl"]
for var i = 0; i < names.count - 1; i+=1 
    NSLog("%@ loves %@", names[i], names[i+1])

很简单的东西。我希望能够获得我所在的索引,并且我喜欢 for 循环在 names.count == 0 时不运行。一口气完成。

但似乎我在 Swift 3 中的选项不允许我这样做。我将不得不做类似的事情:

let names : [String] = ["Jim", "Jenny", "Earl"]
if names.count > 0 
    for i in 0...(names.count - 1) 
        NSLog("%@ loves %@", names[i], names[i+1])
    

需要开头的 if 语句,因为我的程序会在它读取的情况下崩溃: for i in 0...0

我也喜欢无需显式设置索引即可遍历所有内容的想法:

// Pseudocode
for name in names.exceptLastOne 
    NSLog("%@ loves %@", name, name.plus(1))

我觉得有某种语法混合了我的所有需求,但我还没有遇到过。有谁知道一种方法?或者至少是一种让我的代码更紧凑的方法?

更新:有人建议这个问题已经被问过,引用了一个 SO 帖子,其中解决方案是使用某种程度的东西:

for (index, name) in names.enumerated 

与 Hamish 的回答相比,问题在于我只获得了当前名称的索引。这不允许我在不需要执行以下操作的情况下获得 index 处的值:

names[index + 1]

这只是一个需要跟踪的额外变量。我更喜欢 Hamish 的:

for i in names.indices.dropLast() 
    print("\(names[i]) loves \(names[i + 1])")

简短、简单,只需跟踪名称和 i,而不是名称、索引和名称。

【问题讨论】:

swift for loop: for index, element in array?的可能重复 for name in names.dropLast() @LeoDabus 但是OP需要在每次迭代期间从数组中访问两个不同的对象。 for (index, name) in names.dropLast().enumerated() @LeoDabus 发布答案。 【参考方案1】:

一种选择是在数组的indices 上使用dropLast(),允许您迭代除数组的最后一个索引之外的所有CountableRange

let names = ["Jim", "Jenny", "Earl"]

for i in names.indices.dropLast() 
    print("\(names[i]) loves \(names[i + 1])")

如果数组的元素少于两个,则不会进入循环。

另一种选择是zip 包含已删除第一个元素的数组的数组,允许您遍历元素对及其后继元素:

for (nameA, nameB) in zip(names, names.dropFirst()) 
    print("\(nameA) loves \(nameB)")

这利用了zip 截断两个序列中较长的序列(如果它们的长度不相等)这一事实。因此,如果数组的元素少于两个,则再次循环不会进入。

【讨论】:

哇,我不知道 zip!棒极了!也不知道 indicies.dropLast()。肯定会使用它,因为我喜欢引用索引。

以上是关于遍历数组的最后一个索引以外的所有索引的主要内容,如果未能解决你的问题,请参考以下文章

函数不会遍历数组的所有索引[重复]

PHP数组遍历详解

遍历具有不同索引的表单元素名称数组

PHP------定义数组,取值数组和遍历数组

循环遍历数组以获取项目的索引 - swift

循环遍历数组并通过索引添加到另一个数组