Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > C/C++ программирование > Общие вопросы C/C++
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 06.01.2016, 18:36   #1
elf2flash
 
Регистрация: 06.01.2016
Сообщений: 4
По умолчанию Измерение коротких интервалов времени

Есть например некая быстрая функция, время ее выполнения порядка 10нс.
И есть таймер с разрешением 1000нс.
Нужно измерить достаточно точно время выполнения той функции (скажем с дискретом 1 нс).

Самое простое - это конечно же в цикле вызвать функцию, а потом общее время цикла поделить на количество вызовов.

Но есть два ограничения: 1. в цикле эту функцию вызывать нельзя. 2. мерить от начала до конца цикла тоже нельзя.

Есть подсказка: использовать статистику.

Задачку задал начальник (ну он как коллега, просто опыта больше по с/с++), чтоб на праздники не скучно было.
Я уже голову сломал.

При этом изначально мы с ним прорабатывали вопросы измерения временных задержек, что то типа этого:

Код:
for (i=0; i<N; i++)
{
clock_gettime(&start);
any_func();
clock_gettime(&stop);
delta = (stop.tv_sec-start.tv_sec)*(1000000000) + (stop.tv_nsec-start.tv_nsec);
}
с последующим расчетом минимального, максимального, мат. ожидания и СКО для дельты.


В голове крутится задачка изерить короткое расстояние длинной палкой, из школы что-ли, или я уже придумываю...

Последний раз редактировалось Stilet; 06.01.2016 в 18:41.
elf2flash вне форума Ответить с цитированием
Старый 06.01.2016, 19:14   #2
f.hump
C/C++, Asm
Участник клуба
 
Аватар для f.hump
 
Регистрация: 02.03.2010
Сообщений: 1,323
По умолчанию

Цитата:
в цикле эту функцию вызывать нельзя
понятно
Цитата:
мерить от начала до конца цикла тоже нельзя
не понятно

в целом, если можно выполнять тестовую процедуру последовательно с другой процедурой, время выполнения которой можно изменять.
измерить время выполнения двух процедур, для достаточно большого набора конфигураций "другой процедуры". прменить метод наименьших квадратов и узнать таким образом время выполнения тестовой процедуры.
f.hump вне форума Ответить с цитированием
Старый 06.01.2016, 19:55   #3
Smitt&Wesson
Старожил
 
Аватар для Smitt&Wesson
 
Регистрация: 31.05.2010
Сообщений: 13,543
По умолчанию

Я уже сколько раз эту функцию приводил.

Код:
// Таймер замера времени выполнения алгоритма.
enum sign{START, STOP};
void Timer(bool b);

// Таймер замера времени выполнения алгоритма.
// Глобальные переменные для замера временных интервалов.
LARGE_INTEGER freq, time1, time2;
void Timer(bool b)
{
  double span;
  if(b)
  {
  // Снять показания таймера
    QueryPerformanceCounter(&time2);
    time2.QuadPart -= time1.QuadPart;
    span = (double) time2.QuadPart / freq.QuadPart;
    span = span * pow(10,9);
    cout << "Время выполнения: " << span << " мкс\n";
  }
  else
  {
  // Инициировать таймер
    QueryPerformanceFrequency(&freq);
    QueryPerformanceCounter(&time1);
  }
}
Как пользоваться.
Код:
Timer(START);
MyFunction();
Timer(STOP);
Пиши пьяным, редактируй трезвым.
Справочник по алгоритмам С++ Builder

Последний раз редактировалось Smitt&Wesson; 06.01.2016 в 19:57.
Smitt&Wesson вне форума Ответить с цитированием
Старый 06.01.2016, 20:20   #4
min@y™
Цифровой кот
Старожил
 
Аватар для min@y™
 
Регистрация: 29.08.2014
Сообщений: 7,629
По умолчанию

а на какой платформе будет работать программа? я имею в виду многозадачность.
Цитата:
Я уже сколько раз эту функцию приводил.
лет стопицот назад меня попросили на работе тож чото такое накарябать на 5-ом билдыре истчо:
Код:
//---------------------------------------------------------------------------

#ifndef HRTimerH
#define HRTimerH
//---------------------------------------------------------------------------
#include <Windows.hpp>
//---------------------------------------------------------------------------

class THRTimer : public TObject
{
  private:
    double StartTime;
    double ClockRate;
  public:
    bool Exists;                   // Флаг успешного создания таймера
    __fastcall THRTimer();         // Конструктор
    bool __fastcall StartTimer();  // Обнуление таймера
    double __fastcall ReadTimer(); // Чтение значения таймера в миллисекундах
};

extern THRTimer* Timer; // Экземпляр класса - глобальная переменная

void __fastcall InitTimer(void); // Создание таймера
void __fastcall KillTimer(void); // Убиение таймера
double __fastcall HRDelay(const double); // Задержка

#endif
Код:
//---------------------------------------------------------------------------

#include <vcl.h>
#pragma hdrstop

#include "HRTimer.h"

//---------------------------------------------------------------------------

#pragma package(smart_init)

// ------------------------------ Функции модуля -------------------------------

// Задержка.
// ВНИМАНИЕ! Эта функция НЕ создаёт объект таймера. Для создания таймера
// перед первым вызовом HRDelay() вызовите InitTimer(), а после
// последнего вызова HRDelay() освободите память с помощью KillTimer();
double __fastcall HRDelay(const double Milliseconds)
{
  double Result;
  Timer->StartTimer();
  do { Result = Timer->ReadTimer(); } while (Result < Milliseconds);
  return Result;
}

// Создание таймера
void __fastcall InitTimer(void)
{
  Timer = new THRTimer();
}

// Убиение таймера
void __fastcall KillTimer(void)
{
  if (Timer != NULL) delete Timer;
}
// -------------------------- Методы класса THRTimer ---------------------------

// Конструктор
__fastcall THRTimer::THRTimer()
{
  LARGE_INTEGER QW;
  Exists = QueryPerformanceFrequency(&QW);
  ClockRate = QW.QuadPart;
}

// Обнуление таймера
bool __fastcall THRTimer::StartTimer()
{
  LARGE_INTEGER QW;
  bool Result = QueryPerformanceCounter(&QW);
  StartTime = QW.QuadPart;
  return Result;
}

// Чтение времени
double __fastcall THRTimer::ReadTimer()
{
  LARGE_INTEGER ET;
  QueryPerformanceCounter(&ET);
  return 1000.0 * (ET.QuadPart - StartTime) / ClockRate;
}
сказали недавно, что юзают до сих пор этот говнокодъ.
Расскажу я вам, дружочки, как выращивать грибочки: нужно в поле утром рано сдвинуть два куска урана...
min@y™ вне форума Ответить с цитированием
Старый 06.01.2016, 20:36   #5
Smitt&Wesson
Старожил
 
Аватар для Smitt&Wesson
 
Регистрация: 31.05.2010
Сообщений: 13,543
По умолчанию

min@y™. Теореме Пифагора уже более 2000 лет. И что, это говнокод? Вопрос не в том, на чём и как написан, а в том, что работает эффективно.
Пиши пьяным, редактируй трезвым.
Справочник по алгоритмам С++ Builder
Smitt&Wesson вне форума Ответить с цитированием
Старый 06.01.2016, 20:44   #6
min@y™
Цифровой кот
Старожил
 
Аватар для min@y™
 
Регистрация: 29.08.2014
Сообщений: 7,629
По умолчанию

Цитата:
И что, это говнокод? Вопрос не в том, на чём и как написан, а в том, что работает эффективно.
когда этот код писался, мы многоядерных камней с переменной тактовой частотой в глаза не видали. и хрен его знает, как оно там работать будет. я даже и не знаю, как проверить.
Расскажу я вам, дружочки, как выращивать грибочки: нужно в поле утром рано сдвинуть два куска урана...
min@y™ вне форума Ответить с цитированием
Старый 06.01.2016, 20:56   #7
Smitt&Wesson
Старожил
 
Аватар для Smitt&Wesson
 
Регистрация: 31.05.2010
Сообщений: 13,543
По умолчанию

Цитата:
Сообщение от min@y™ Посмотреть сообщение
когда этот код писался, мы многоядерных камней с переменной тактовой частотой в глаза не видали. и хрен его знает, как оно там работать будет. я даже и не знаю, как проверить.
Если считаешь, что ядра делят задачу на их количество, то сильно ошибаешься. Каждому ядру, присваивается поток, который оно (ядро) и обрабатывает. Да, каждый поток, может прерываться супервизором Винды, но не в том коде, который я привёл. Я сильно не вникал в сам процесс, но экспериментально, один и тот-же массив в 100 элементов, сортируется примерно за одно и то-же время. Разница в 1 микросекунду. Это много меньше, чем квант, который выделяет винда на обработку очередного потока. Говорю, не особо вникал, но похоже код, который я привёл (он не мой), свой участок делает привелегированным. Т.е. Винда не может его прервать.
Пиши пьяным, редактируй трезвым.
Справочник по алгоритмам С++ Builder
Smitt&Wesson вне форума Ответить с цитированием
Старый 06.01.2016, 21:22   #8
min@y™
Цифровой кот
Старожил
 
Аватар для min@y™
 
Регистрация: 29.08.2014
Сообщений: 7,629
По умолчанию

Цитата:
Если считаешь, что ядра делят задачу на их количество, то сильно ошибаешься. Каждому ядру, присваивается поток, который оно (ядро) и обрабатывает. Да, каждый поток, может прерываться супервизором Винды, но не в том коде, который я привёл. Я сильно не вникал в сам процесс, но экспериментально, один и тот-же массив в 100 элементов, сортируется примерно за одно и то-же время. Разница в 1 микросекунду. Это много меньше, чем квант, который выделяет винда на обработку очередного потока. Говорю, не особо вникал, но похоже код, который я привёл (он не мой), свой участок делает привелегированным. Т.е. Винда не может его прервать.
да не напрягайся. мне всё_равно.
Расскажу я вам, дружочки, как выращивать грибочки: нужно в поле утром рано сдвинуть два куска урана...
min@y™ вне форума Ответить с цитированием
Старый 06.01.2016, 21:54   #9
elf2flash
 
Регистрация: 06.01.2016
Сообщений: 4
По умолчанию

Цитата:
Сообщение от f.hump Посмотреть сообщение
понятно

не понятно

в целом, если можно выполнять тестовую процедуру последовательно с другой процедурой, время выполнения которой можно изменять.
измерить время выполнения двух процедур, для достаточно большого набора конфигураций "другой процедуры". прменить метод наименьших квадратов и узнать таким образом время выполнения тестовой процедуры.
Я о таком тоже думал. Вот есть такая функция как nanosleep().
Упрощенно:
Вызвал свою функцию, затем nanosleep(1960). Померил время - получил 1000нс. Хорошо, значит надо больше 1960 в nanosleep сувать.
Вызвал свою функцию, затем nanosleep(1970). Померил время - получил 2000нс. О, значит моя функция где-то 30нс выполняется.
Надеюсь понятно изложил мысль.
Вот только nanosleep, usleep и тому подобное не точное время работают, и нет уверенности, что nanosleep(1970) ровно на 1970нс остановит программу, может и на 2343нс уснет...


По поводу платформы. Конечный код нацелен на линукс х64. Но сегодня проект собирал дома под линукс х32, а также под вин7 х64.

По замерам времени у меня получается, что два вызова подряд функции
Код:
clock_gettime(CLOCK_MONOTONIC,&start);
clock_gettime(CLOCK_MONOTONIC,&stop);
дает минимум 44нс.
Но в условиях задачи вообще абстрактный таймер с дискретом 1000нс...
elf2flash вне форума Ответить с цитированием
Старый 06.01.2016, 22:00   #10
min@y™
Цифровой кот
Старожил
 
Аватар для min@y™
 
Регистрация: 29.08.2014
Сообщений: 7,629
По умолчанию

Цитата:
таймер с дискретом 1000нс...
Думаю, что это невозможно.
Расскажу я вам, дружочки, как выращивать грибочки: нужно в поле утром рано сдвинуть два куска урана...
min@y™ вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Измерение времени выполнения процедуры Silverstone Помощь студентам 5 18.03.2012 22:02
Профилирование (Измерение времени работы программы) megakatapuz Общие вопросы C/C++ 0 06.01.2010 23:04
Измерение времени выполнения цикла Alexcomeback Общие вопросы C/C++ 10 25.04.2009 16:58
Измерение времени нажатия клавиши клавиатуры buka_14 Помощь студентам 6 13.04.2009 13:18
Измерение времени в c# byte916 Помощь студентам 4 06.03.2009 21:18