Я провела серию тестов новой библиотеки.
Всё отлично работает: даже под вендой можно вести наносекундные измерения!
Для этого теста надо собрать буст с флагом
BOOST_DATE_TIME_POSIX_TIME_STD_CONFIG (и сам тест с этим же флагом, соответственно), чтобы
ptime давал наносекундное разрешение. В принципе, можно и вообще без него обойтись, тайминги нормально считаются в
boost::chrono (в
ptime под вендой - нет, даже с флагом). Я сделала через
ptime для
this_thread::sleep() в моих рабочих программах: сам
boost::chrono в
boost::thread напрямую пока не поддерживается, но будет.
Конверсия стащена из песочницы буста и чуть переделана. Скоро это уже всё будет в самом бусте, без самодельных велосипедов. В рабочей версии уже многое переделано и добавлено, я наблюдаю за прогрессом.
Итак, код теста для венды (для линя проведу тест дома, чуть позже, в коде практически ничего не нужно менять):
#include <Windows.h>
#include <boost/date_time/posix_time/posix_time.hpp>
#include <boost/chrono.hpp>
#include <vector>
using namespace std;
using namespace boost;
template < typename Duration>
posix_time::ptime convert_time_point_to_ptime(const chrono::time_point<chrono::high_resolution_clock, Duration>& from)
{
typedef chrono::time_point<chrono::high_resolution_clock, Duration> time_point_t;
typedef chrono::nanoseconds duration_t;
typedef duration_t::rep rep_t;
rep_t d = chrono::duration_cast<duration_t>(from.time_since_epoch()).count();
rep_t sec = d/1000000000;
rep_t nsec = d%1000000000;
return posix_time::from_time_t(0)+
posix_time::seconds(static_cast<long>(sec))+
#ifdef BOOST_DATE_TIME_HAS_NANOSECONDS
posix_time::nanoseconds(nsec);
#else
posix_time::microseconds((nsec+500)/1000);
#endif
}
posix_time::ptime get_current_time()
{
chrono::high_resolution_clock::time_point tp = chrono::high_resolution_clock::now();
posix_time::ptime pt=convert_time_point_to_ptime(tp);
return pt;
}
int main(int argc, char* argv[])
{
int res = SetThreadPriority(GetCurrentThread(),THREAD_PRIORITY_TIME_CRITICAL);
if(res != 0)
{
cout <<"Real time priority set" << endl;
}
vector <posix_time::time_duration> delays;
for(int i=0; i<100; i++)
{
posix_time::ptime t = get_current_time();
posix_time::time_duration d = t.time_of_day();
delays.push_back(d);
}
res = SetThreadPriority(GetCurrentThread(),THREAD_PRIORITY_NORMAL);
if(res != 0)
{
cout <<"Normal priority set" << endl;
}
posix_time::time_duration prev_d;
for(vector<posix_time::time_duration>::iterator iter=delays.begin(); iter != delays.end(); iter++)
{
cout << iter->total_nanoseconds() - prev_d.total_nanoseconds() << endl;
prev_d = *iter;
}
return 0;
}
Под вендой (семёрка, 64, core2duo 2.6GHz, release win32) получен результат:
(первое значение - мусор)
Real time priority set
Normal priority set
12589068513489
4332
1575
1575
1182
1181
394
1575
394
788
1181
394
788
788
1575
394
787
394
788
394
1575
788
393
788
394
787
788
394
788
1181
788
787
394
788
394
787
394
788
394
787
394
788
394
1575
787
394
394
788
394
787
788
394
787
394
788
394
787
394
788
394
787
394
788
394
1575
787
788
394
788
393
788
394
788
393
788
394
787
394
788
394
787
394
788
394
787
394
788
394
787
394
788
394
787
394
788
1181
788
787
394
788
Причём если запускать ещё сам процесс с REALTIME приоритетом, то выходит примерно то же самое, но без выскоков за 2 мкс:
Real time priority set
Normal priority set
12645134127255
3938
1575
788
788
1181
394
788
787
394
788
394
787
394
788
787
394
394
394
394
1181
394
788
393
394
394
394
788
393
788
788
394
393
394
394
394
787
394
394
394
394
787
394
1182
394
393
394
394
788
393
394
394
394
394
787
394
394
394
394
787
394
394
394
394
1181
394
788
393
394
394
394
788
393
394
394
394
394
393
788
394
394
394
393
394
788
394
394
393
394
788
394
393
394
394
394
1575
394
394
788
393
Собственно, это и есть предельная скорость работы венды при тупом поллинге в консоли. Кстати, проц при этом загружен только на 50%. Видимо, полностью грузит одно из ядер. Можно было даже выделить потоку отдельный проц, но мне стало лень, а для теста это несущественно.