У меня есть приложение, которое должно передавать пакеты через фиксированные интервалы 33 мс +/- несколько миллисекунд.
Итак, я придумал класс SpinTimer
, показанный ниже:
class SpinTimer
{
public void SpinWait(double waitTimeInSeconds)
{
if (waitTimeInSeconds < 0.0)
{
throw new ArgumentOutOfRangeException("waitTimeInSeconds", "Must be >= 0.0");
}
Stopwatch timer = new Stopwatch();
double elapsed = 0.0;
timer.Start();
do
{
elapsed = (double)timer.ElapsedTicks / (double)Stopwatch.Frequency;
} while (elapsed < waitTimeInSeconds);
}
}
Однако после профилирования кода я обнаружил, что вызов System.Diagnostics.Stopwatch.GetTimestamp()
занимает большую часть времени выполнения. Как примечание, я не могу позволить себе спящий поток и переключение контекста, так как это вызывает слишком большое "дрожание" в скорости вывода.
Замечания о запуске профиля:
- Приоритет нити был установлен на
ThreadPriority.Highest
- Приоритет процесса был установлен на
ProcessPriorityClass.High
Исходная программа, которую я написал (на C ++), достигла того же эффекта, используя функции QueryPerformanceCounter()
и QueryPerformanceFrequency()
. Должен ли я использовать эти вызовы с PInvoke вместо класса Stopwatch
? Или есть другой подходящий способ сделать это?
Спасибо!