///|
fn StringView::parse_int_part(self : StringView) -> Int? {
Some(@string.parse_int(self)) catch {
_ => None
}
}
///|
fn StringView::parse_float_part(self : StringView) -> Float? {
Some(Float::from_double(@string.parse_double(self))) catch {
_ => None
}
}
///|
/// Parse a `used,total` pair in GiB, e.g. `"46.3,128"`.
fn String::parse_memory(self : String) -> Memory? {
guard self.split_once(",") is Some((used_s, total_s)) else { return None }
guard used_s.parse_float_part() is Some(used) else { return None }
guard total_s.parse_float_part() is Some(total) else { return None }
Some({ used, total })
}
///|
/// Parse a `width,height` pair, e.g. `"3456,2234"`.
fn String::parse_resolution(self : String) -> Resolution? {
guard self.split_once(",") is Some((width_s, height_s)) else { return None }
guard width_s.parse_int_part() is Some(width) else { return None }
guard height_s.parse_int_part() is Some(height) else { return None }
Some({ width, height })
}
///|
/// Parse an `hours,mins` pair, e.g. `"3,12"`.
fn String::parse_uptime(self : String) -> Uptime? {
guard self.split_once(",") is Some((hours_s, mins_s)) else { return None }
guard hours_s.parse_int_part() is Some(hours) else { return None }
guard mins_s.parse_int_part() is Some(mins) else { return None }
Some({ hours, mins })
}
///|
/// Parse `name,cores,clock` in GHz, e.g. `"Apple M3 Max,16,4.05"`.
fn String::parse_cpu(self : String) -> Cpu? {
let parts = self.split(",").to_array()
guard parts.length() == 3 else { return None }
guard parts[1].parse_int_part() is Some(cores) else { return None }
guard parts[2].parse_float_part() is Some(clock) else { return None }
Some({ name: parts[0].to_owned(), cores, clock })
}
///|
/// Parse `name` or `name,vram` in GB, e.g. `"Apple M3 Max"` or `"RTX 4090,24"`.
fn String::parse_gpu(self : String) -> Gpu? {
match self.split_once(",") {
Some((name_s, vram_s)) => {
guard vram_s.parse_int_part() is Some(vram) else { return None }
Some({ name: name_s.to_owned(), vram })
}
None => Some({ name: self, vram: 0 })
}
}