簡體   English   中英

在序列數組中分離奇數和偶數索引

[英]Separate odd and even indexes in a sequence array

for循環中的for不起作用,因為int類型不符合協議序列。

我有3個數組:

1個主數組,存儲數組

1個奇數陣,開頭為空

1個偶數組,開頭為空

意思是主陣列的所有奇數索引將存儲在奇數陣列中,而偶數陣列則相同。

    while i < masterA.count {
        evenA.append(masterA[i])
        if i > 0{
        oddA.append(masterA[i - 1])
        }
        i += 2
    }

然而,這不夠好。 誰有更好的主意?

這是另一種可能的解決方案

let evenA = stride(from: 0, to: masterA.count, by: 2).map { masterA[$0] }
let oddA = stride(from: 1, to: masterA.count, by: 2).map { masterA[$0] }

元素直接從源陣列中的偶數/奇數位置“拾取”。

表現比較:

我簡單而不是非常復雜的特殊基准測試代碼:

import Swift

let N = 10_000_000
let RUNS = 50

let masterA = (0..<N).map { $0 }

var times = (0.0, 0.0, 0.0, 0.0)
for _ in 1...RUNS {

    // filter+map (dfri)
    do {
        let start = Date()
        let evenA = masterA.enumerated().filter { $0.0 % 2 == 0 }.map{ $0.1 }
        let oddA = masterA.enumerated().filter { $0.0 % 2 != 0 }.map{ $0.1 }
        let time = Date().timeIntervalSince(start)
        times.0 += time
    }

    // flatMap (dfri)
    do {
        let start = Date()
        let evenA = masterA.enumerated().flatMap { $0 % 2 == 0 ? $1 : nil }
        let oddA = masterA.enumerated().flatMap { $0 % 2 != 0 ? $1 : nil }
        let time = Date().timeIntervalSince(start)
        times.1 += time
    }

    // stride+map (me)
    do {
        let start = Date()
        let evenA = stride(from: 0, to: masterA.count, by: 2).map { masterA[$0] }
        let oddA = stride(from: 1, to: masterA.count, by: 2).map { masterA[$0] }
        let time = Date().timeIntervalSince(start)
        times.2 += time
    }

    // loop (Keiwan)
    do {
        let start = Date()
        var evenA = [Int]()
        var oddA = [Int]()

        for (index, element) in masterA.enumerated() {
            if index % 2 == 0 {
                evenA.append(element)
            } else {
                oddA.append(element)
            }
        }
        let time = Date().timeIntervalSince(start)
        times.3 += time
    }
}

print(N, RUNS)
print(times.0/Double(RUNS), times.1/Double(RUNS), times.2/Double(RUNS), times.3/Double(RUNS))

結果:(在MacBook上,在發布模式下運行)

#elements   filter+map  flatMap   stride+map  loop
10,000      0.0001      0.00008   0.00004     0.00004
100,000     0.0016      0.0008    0.0004      0.0004
1,000,000   0.0295      0.0136    0.0090      0.0091
10,000,000  0.3025      0.1332    0.0909      0.1250

在循環時,您可以使用enumerated()來獲取索引和值:

for (index, element) in masterA.enumerated() {
    if index % 2 == 0 {
        evenA.append(element)
    } else {
        oddA.append(element)
    }
}

這將存儲masterA每個element ,其中奇數索引在oddA ,每個元素在evenA具有偶數索引。

可能我誤解了你的意圖,但似乎你想要將具有奇數索引的masterA 元素存儲在oddA ,相反,具有偶數索引的masterA元素應該存儲在evenA

您可以通過過濾實現這一masterA WRT的指數masterA ,隨時可從masterA.enumerated()

let masterA = [4, 5, 2, 1, 7, 8, 1]

let evenA = masterA.enumerated().filter { $0.0 % 2 == 0 }.map{ $0.1 }
let oddA = masterA.enumerated().filter { $0.0 % 2 != 0 }.map{ $0.1 }

print(evenA) // [4, 2, 7, 1]
print(oddA)  // [5, 1, 8]

正如@Hamish在下面的評論中指出的那樣,我們可以使用compactMap (Swift 3: flatMap )作為鏈式filtermap的替代方案。

let evenA = masterA.enumerated().compactMap { $0 % 2 == 0 ? $1 : nil }
let oddA = masterA.enumerated().compactMap { $0 % 2 != 0 ? $1 : nil }

后一個compactMap解決方案更簡潔,而filter ... map解決方案可能顯示意圖稍微清晰。 在這個特殊的簡潔與語義競爭中,我個人更喜歡compactMap解決方案。

另一種方法

Swift 3.0代碼

let array = [1,2,3,4,5,6,7,8]
var oddArray = [Int]()
var evenArray = [Int]()

for (index,value) in array.enumerated() {
    if index % 2 == 0 {
        // It is odd because index starts from 0 in array and I am assuming the 0 index as the odd one.
        oddArray.append(value)
    } else {
        evenArray.append(value)
    }
}

奇數陣= [1,3,5,7]
甚至數組= [2,4,6,8]

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM