2017-01-03 2 views
0
#include <chrono> 

int main() 
{ 
    using clock = std::chrono::system_clock; 
    using time_point = std::chrono::time_point<clock>; 

    auto tp_now = clock::now(); 
    auto tp_min = time_point::min(); 

    bool b1 = tp_now > tp_min; 
    bool b2 = (tp_now - tp_min) > std::chrono::seconds{ 0 }; 
    cout << boolalpha << b1 << endl << b2 << endl; 
} 

Ожидаемый результат:Почему std :: chrono :: time_point не ведет себя так, как ожидалось?

правда

правда

Но фактический выход:

верно

фа lse

Почему именно std::chrono::time_point не работает должным образом?

+1

Coliru: http://coliru.stacked-crooked.com/a/4ee25ea413140aa8 Во всяком случае, Wandbox напечатано верно неверно – Danh

+2

Я думаю, что это целочисленное переполнение – Danh

+1

'tp_now - tp_min' отрицательный на Wandbox. Я думаю, что Дэн прав. –

ответ

2

С:

using clock = std::chrono::system_clock; 
using time_point = std::chrono::time_point<clock>; 

time_point реализуется как если он хранит значение типа Длительность указывающей интервал времени от начала эпохи для часов. (См std::chrono::time_point)

Тип duration членом clock (и из time_point) способен представлять отрицательные длительности.

Таким образом, duration в вашей реализации может быть реализован с помощью целочисленного целочисленного символа (он может быть реализован с целым числом без знака, но со сложным сравнением).

В этой конкретной реализации

time_point::min(); 
time_point t(clock::duration::min()); 
time_point t(clock::duration(std::numeric_limits<Rep>::lowest())); 

и tp_now больше zero, таким образом, когда вы вычитать их, вы получите целочисленное переполнение, так как результат больше, чем std::numeric_limits<Rep>::max(). В реализации с подписанным back-end, это неопределенное поведение, в реализации с неподписанным back-end, я не знаю об этом, но, я думаю, его специальное сравнение сделает его false.

В this example, tp_min является -9223372036854775808 тиков от своей эпохи, что число совпадает с std::numeric_limits<duration::rep>::lowest()


TL; DR; Это целочисленное переполнение. Не используйте

(tp1 - tp2) > std::chrono::duration<whatever_rep>::zero 

Вместо этого используйте

tp1 > tp2 
Смежные вопросы