Вопрос

Мне просто было интересно, есть ли элегантный способ установить максимальную загрузку процессора для определенного потока, выполняющего интенсивные вычисления.

Прямо сейчас я нашел наиболее трудоемкий цикл в потоке (он выполняет только сжатие) и использую GetTickCount() и Sleep() с жестко закодированными значениями.Это гарантирует, что цикл продолжается в течение определенного периода времени, а затем переходит в спящий режим в течение определенного минимального времени.Это более или менее выполняет свою работу, т.е.гарантирует, что поток не будет использовать более 50% процессора.
Однако поведение зависит от количества ядер процессора (огромный недостаток) и просто уродливое (меньший недостаток :)).
Есть какие-нибудь идеи?

Это было полезно?

Решение

Я не знаю ни одного API, который мог бы заставить планировщик ОС делать то, что вы хотите (даже если ваш поток имеет приоритет ожидания, если нет готовых потоков с более высоким приоритетом, ваш будет запущен).Тем не менее, я думаю, вы можете импровизировать довольно элегантную функцию регулирования, основанную на том, что вы уже делаете.По сути (у меня нет под рукой компьютера для разработки Windows):

Выберите количество времени по умолчанию, в течение которого поток будет находиться в режиме ожидания на каждой итерации.Затем, на каждой итерации (или на каждой n-й итерации, так что функция регулирования сама по себе не становится значительной нагрузкой на процессор),

  1. Вычислите количество процессорного времени, которое использовал ваш поток с момента последнего вызова вашей функции регулирования (я буду называть это dCPU).Вы можете использовать GetThreadTimes() API для получения количества времени, в течение которого выполнялся ваш поток.
  2. Вычислите количество реального времени, прошедшего с момента последнего вызова вашей функции регулирования (я буду называть это dCLOCK).
  3. dCPU / dCLOCK - это процент загрузки процессора (одного процессора).Если оно выше, чем вы хотите, увеличьте время сна, если ниже, уменьшите время сна.
  4. Переведите ваш поток в спящий режим на вычисленное время.

В зависимости от того, как ваш сторожевой таймер вычисляет загрузку процессора, вы можете захотеть использовать GetProcessAffinityMask() чтобы узнать, сколько процессоров в системе.dCPU / (dCLOCK * процессоры) - процент от общего доступного процессорного времени.

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

Другие советы

В Linux вы можете изменить приоритет планирования потока с помощью nice().

Я не могу придумать какой-либо кроссплатформенный способ того, что вы хотите (или какой-либо гарантированный способ полной остановки), но поскольку вы используете GetTickCount, возможно, вас не интересует кроссплатформенность :)

Я бы использовал межпроцессные коммуникации и установил хорошие уровни интенсивности процессов, чтобы получить то, что вам требуется, но я не уверен, что это подходит для вашей ситуации.

Редактировать:Я согласен с Бернард вот почему я думаю, что процесс, а не поток, может быть более подходящим, но он просто может не соответствовать вашим целям.

Проблема в том, что ненормально оставлять процессор в режиме ожидания, пока у вас есть работа.Обычно вы устанавливаете фоновой задаче приоритет ОЖИДАНИЯ и позволяете операционной системе планировать для нее все процессорное время, которое не используется интерактивными задачами.

Мне кажется, что проблема в сторожевом процессе.

Если ваша фоновая задача привязана к процессору, то вы хотите, чтобы она использовала все неиспользуемое процессорное время для своей задачи.

Может быть, вам стоит взглянуть на исправление сторожевой программы?

Возможно, вы сможете изменить приоритет потока, но изменение максимального использования потребует либо опроса и взломов, чтобы ограничить количество происходящих событий, либо использования инструментов операционной системы, которые могут установить максимальное использование процесса.Однако я не вижу никаких обстоятельств, при которых вы захотели бы это сделать.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top