A for in loop won't work because type int is does not conform to protocol Sequence.
I have 3 arrays:
1 master array, where the array is stored
1 odd array, empty at the beginning
1 even array, empty at the beginning
The meaning is that all the odd indexes of the master array will be stored at the odd array, and the same for the even array.
while i < masterA.count {
evenA.append(masterA[i])
if i > 0{
oddA.append(masterA[i - 1])
}
i += 2
}
However this does not work good enough. Anyone has a better idea?
Here is another possible solution:
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] }
The elements are "picked" directly from the even/odd positions in the source array.
Performance comparison:
My simple, not very sophisticated ad-hoc benchmarking code:
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))
Results: (On a MacBook, running in Release mode)
#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
You can use enumerated()
to get both the index and the value while looping:
for (index, element) in masterA.enumerated() {
if index % 2 == 0 {
evenA.append(element)
} else {
oddA.append(element)
}
}
This will store every element
of masterA
with an odd index in oddA
and every element with an even index in evenA
.
Possibly I'm misunderstanding your intent, but it seems as if you want that elements of masterA
that have odd indices should be stored in oddA
, and conversely, elements of masterA
that have even indices should be stored in evenA
.
You can achieve this by filtering masterA
wrt the indices of masterA
, readily available from 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]
As @Hamish points out in his comment below, we could use the compactMap
(Swift 3: flatMap
) as an alternative to the chained filter
and map
.
let evenA = masterA.enumerated().compactMap { $0 % 2 == 0 ? $1 : nil }
let oddA = masterA.enumerated().compactMap { $0 % 2 != 0 ? $1 : nil }
The latter compactMap
solution is briefer, whereas the filter
... map
solution possibly shows intent slightly clearer. In this particular brevity vs. semantics competition, I would personally prefer the compactMap
solution.
Another solution
Swift 3.0 code
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)
}
}
Odd Array = [1,3,5,7]
Even Array = [2,4,6,8]
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.