Reputation: 9351
My code works as intended, I am just trying to speed things up.
I have a database table which contains millions of sensor measurements. When I query the database for the measurements (sorted by the sensor's name) of the past 2 months, I get roughly 300,000 results.
I then proceed to step through the results and want to create nested struct objects from the data. Here some shorter pseudo-code:
struct Measurement {
var date: Int
var temp: Double?
...
}
struct Sensor {
var sensorName: String
var measurements: [Measurement]
}
var sensors:[Sensor] = []
...
for r in dbResults {
...
let m = Measurement(date: r.date, temp: r.temp1, ... )
if let index = sensors.firstIndex(where: { $0.sensorName = r.name }) {
sensors[index].measurements.append(m)
} else {
sensors.append(Sensor(sensorName: r.name, measurements: [m]))
}
}
This is however fairly slow. It takes about a minute for the loop to get done.
Is there a way to speed this process up? I am assuming .firstIndex
takes too long.
I was thinking about creating the objects on parallel threads, but I wasn't sure how to best do that, without risking a race condition when checking the .firstIndex
.
Thanks for any ideas
Upvotes: 1
Views: 61
Reputation:
Don't rewrite Dictionary(grouping:by:)
yourself. Somebody else maintains that for you for free!!
Put that var
here while you're at it: 🗑
let sensors = Dictionary(grouping: dbResults, by: \.name).map {
Sensor(
sensorName: $0,
measurements: $1.map { .init(date: $0.date, temp: $0.temp1) }
)
}
Upvotes: 0
Reputation: 257729
I would change storage to dictionary
var sensors:[String: Sensor] = [:]
...
for r in dbResults {
...
let m = Measurement(date: r.date, temp: r.temp1, ... )
sensors[r.name, default: Sensor(sensorName: r.name,
measurements: [])].measurements.append(m)
}
Upvotes: 1