Reputation: 13063
I looked here: Swift 3 - Reduce a collection of objects by an Int property and here: https://medium.com/@abhimuralidharan/higher-order-functions-in-swift-filter-map-reduce-flatmap-1837646a63e8 but I can not get reduce to work. Edit: Maybe because they changed the way the code compiles in swift 4 (which I am using) https://stackoverflow.com/a/46432554/7715250
This is because I get this error:
Contextual closure type '(_, Test) -> _' expects 2 arguments, but 1 was used in closure body
This is my class:
class Test {
let amountLeftToDownload: Int
let amountDownloaded: Int
init(amountLeftToDownload: Int, amountDownloaded: Int) {
self.amountLeftToDownload = amountLeftToDownload
self.amountDownloaded = amountDownloaded
}
}
I have an array of it (progress). I want to get the total count of downloads, which is amountLeftToDownload + amountDownloaded for each Test instance. I tried this:
let totalDownloadsToProcess = progress.reduce(0) {$0.amountLeftToDownload, $0.amountDownloaded }
I replace the comma for a +, and a few other things but it wont work.
Upvotes: 1
Views: 301
Reputation: 154651
The closure passed to reduce
takes 2 arguments: the first is the accumulator, and the second is an element from the array you are reducing. So you need to add the values from the current record to the current total:
let totalDownloadsToProcess = progress.reduce(0) { $0 + $1.amountLeftToDownload + $1.amountDownloaded }
It might be clearer if you name the inputs:
let totalDownloadsToProcess = progress.reduce(0) { totalSoFar, elem in totalSoFar + elem.amountLeftToDownload + elem.amountDownloaded }
The closure gets called for each element in the array. At each step, it returns a new value that gets passed in as totalSoFar
when the next element is processed. The 0
is used as the initial value for totalSoFar
when the first element is processed.
Upvotes: 2