Что такое mach_absolute_time на основе iPhone
Я использую этот код для отслеживания последней перезагрузки:
+ (float) secondsSinceLastReboot{
return ((float)(mach_absolute_time())) * ((float)timebase.numer) / ((float)timebase.denom) / 1000000000.0f;
}
Я предположил, что mach_absolute_time() основывается на последнем времени загрузки устройства, как на mac. Похоже, что это не основано на этом. На самом деле я понятия не имею, на чем он основан.
Посмотрите на следующее поведение (сегодня дата 2009-09-20):
lastRebootTime = [[NSDate date] addTimeInterval:-[self secondsSinceLastReboot]];
//last Reboot Time will contain : 2009-09-20 07:42:14 +0100
Я абсолютно уверен, что я не перезагрузил свое устройство в то время. Мое устройство не загружалось через неделю.
Кроме того, когда я отсоединяю свое устройство от кабеля и запускаю это приложение, кажется, что когда устройство переходит в режим сна, lastRebootTime начинает смещаться в будущем. Кажется, что mach_absolute_time не учитывает время сна. Или я ошибаюсь?
Мне бы очень хотелось получить временную метку, когда устройство перезагрузилось. Любая идея?
Ответы
Ответ 1
У меня были проблемы с этим. Существует не так много хорошей документации, поэтому я пошел с экспериментированием. Вот что я смог определить:
mach_absolute_time зависит от процессора устройства. Он возвращает тики с момента последней перезагрузки устройства (иначе это называется временем безотказной работы). Чтобы получить его в понятной для человека форме, вы должны изменить его по результату mach_timebase_info (отношение), которое вернет миллиардную долю секунд (или наносекунды). Чтобы сделать это более удобным, я использую функцию, подобную приведенной ниже:
#include <mach/mach_time.h>
int getUptimeInMilliseconds()
{
const int64_t kOneMillion = 1000 * 1000;
static mach_timebase_info_data_t s_timebase_info;
static dispatch_once_t onceToken;
dispatch_once(&onceToken, ^{
(void) mach_timebase_info(&s_timebase_info);
});
// mach_absolute_time() returns billionth of seconds,
// so divide by one million to get milliseconds
return (int)((mach_absolute_time() * s_timebase_info.numer) / (kOneMillion * s_timebase_info.denom));
}
Ответ 2
Если вам не все равно о времени вычислений, вы можете использовать простой класс Obj-C из Foundation
NSTimeInterval systemUptime = [[NSProcessInfo processInfo] systemUptime];
Ответ 3
Если кому-то это нужно в Swift (работает в 4.2 и 5.0).
let beginTime = mach_absolute_time()
// do something...
var baseInfo = mach_timebase_info_data_t(numer: 0, denom: 0)
if mach_timebase_info(&baseInfo) == KERN_SUCCESS {
let finiTime = mach_absolute_time()
let nano = (finiTime - beginTime) * UInt64(baseInfo.numer) / UInt64(baseInfo.denom)
}