Приоритеты планирования
Потоки планируются на основе их приоритета планирования. Каждому потоку назначается приоритет планирования. Уровни приоритета варьируются от нуля (самый низкий приоритет) до 31 (наивысший приоритет). Только поток с нулевой страницей может иметь нулевой приоритет. (Поток нулевой страницы — это системный поток, отвечающий за обнуление всех свободных страниц, если нет других потоков, которые должны выполняться.)
Система рассматривает все потоки с одинаковым приоритетом как равные. Система назначает временные срезы циклическим перебором всем потокам с наивысшим приоритетом. Если ни один из этих потоков не готов к запуску, система назначает срезы времени циклическим перебором всем потокам со следующим наивысшим приоритетом. Если поток с более высоким приоритетом становится доступным для выполнения, система перестает выполнять поток с более низким приоритетом (не позволяя ей завершить использование среза времени) и назначает срез полного времени потоку с более высоким приоритетом. Дополнительные сведения см. в разделе Контекстные коммутаторы.
Приоритет каждого потока определяется следующими критериями:
- Класс приоритета процесса
- Уровень приоритета потока в классе приоритета процесса.
Класс и уровень приоритета объединяются для формирования базового приоритета потока. Сведения о динамическом приоритете потока см. в разделе Повышение приоритета.
Класс Priority
Каждый процесс принадлежит к одному из следующих классов приоритетов:
- IDLE_PRIORITY_CLASS
BELOW_NORMAL_PRIORITY_CLASS
NORMAL_PRIORITY_CLASS
ABOVE_NORMAL_PRIORITY_CLASS
HIGH_PRIORITY_CLASS
REALTIME_PRIORITY_CLASS
По умолчанию класс приоритета процесса — NORMAL_PRIORITY_CLASS. Используйте функцию CreateProcess , чтобы указать класс приоритета дочернего процесса при его создании. Если вызывающий процесс IDLE_PRIORITY_CLASS или BELOW_NORMAL_PRIORITY_CLASS, новый процесс наследует этот класс. Используйте функцию GetPriorityClass для определения текущего класса приоритета процесса и функцию SetPriorityClass , чтобы изменить класс приоритета процесса.
Процессы, которые отслеживают систему, такие как экранные заставки или приложения, которые периодически обновляют дисплей, должны использовать IDLE_PRIORITY_CLASS. Это не позволяет потокам этого процесса, которые не имеют высокого приоритета, мешать потокам с более высоким приоритетом.
Используйте HIGH_PRIORITY_CLASS с осторожностью. Если поток выполняется с наивысшим приоритетом в течение длительных периодов времени, другие потоки в системе не будут получать процессорное время. Если несколько потоков заданы с высоким приоритетом одновременно, потоки теряют свою эффективность. Класс с высоким приоритетом следует зарезервировать для потоков, которые должны реагировать на критически важные по времени события. Если приложение выполняет одну задачу, требующую высокоприоритетного класса, а остальные задачи имеют обычный приоритет, используйте SetPriorityClass , чтобы временно повысить класс приоритета приложения. затем уменьшите его после завершения критически важной по времени задачи. Другая стратегия заключается в создании высокоприоритетного процесса, который большую часть времени блокирует все его потоки, пробуждая потоки только тогда, когда требуются критические задачи. Важно то, что высокоприоритетный поток должен выполняться в течение короткого времени и только в том случае, если требуется выполнить критически важную по времени работу.
Почти никогда не следует использовать REALTIME_PRIORITY_CLASS, так как это прерывает системные потоки, управляющие вводом с помощью мыши, вводом с клавиатуры и фоновой очисткой диска. Этот класс может подходить для приложений, которые "разговаривают" напрямую с оборудованием или выполняют короткие задачи, которые должны иметь ограниченные перерывы.
Уровень приоритета
Ниже приведены уровни приоритета в каждом классе приоритета.
- THREAD_PRIORITY_IDLE
THREAD_PRIORITY_LOWEST
THREAD_PRIORITY_BELOW_NORMAL
THREAD_PRIORITY_NORMAL
THREAD_PRIORITY_ABOVE_NORMAL
THREAD_PRIORITY_HIGHEST
THREAD_PRIORITY_TIME_CRITICAL
Все потоки создаются с помощью THREAD_PRIORITY_NORMAL. Это означает, что приоритет потока совпадает с классом приоритета процесса. После создания потока используйте функцию SetThreadPriority , чтобы настроить его приоритет относительно других потоков в процессе.
Типичная стратегия заключается в использовании THREAD_PRIORITY_ABOVE_NORMAL или THREAD_PRIORITY_HIGHEST для потока ввода процесса, чтобы обеспечить реагирование приложения на запросы пользователя. Фоновые потоки, особенно те, которые интенсивно используют процессор, можно задать для THREAD_PRIORITY_BELOW_NORMAL или THREAD_PRIORITY_LOWEST, чтобы обеспечить их вытеснять при необходимости. Однако если у вас есть поток, ожидающий другого потока с более низким приоритетом для выполнения какой-то задачи, обязательно заблокируйте выполнение ожидающего потока с высоким приоритетом. Для этого используйте функцию ожидания, критический раздел или функцию Sleep , SleepEx или SwitchToThread . Это предпочтительнее, чем выполнение цикла потока. В противном случае процесс может оказаться взаимоблокировкой, так как поток с более низким приоритетом никогда не планируется.
Чтобы определить текущий уровень приоритета потока, используйте функцию GetThreadPriority .
Базовый приоритет
Класс приоритета процесса и уровень приоритета потока объединяются для формирования базового приоритета каждого потока.
В следующей таблице показан базовый приоритет для сочетаний класса приоритета процесса и значения приоритета потока.
Класс приоритета процесса | Уровень приоритета потока | Базовый приоритет | |
---|---|---|---|
IDLE_PRIORITY_CLASS | THREAD_PRIORITY_IDLE | 1 | |
THREAD_PRIORITY_LOWEST | 2 | ||
THREAD_PRIORITY_BELOW_NORMAL | 3 | ||
THREAD_PRIORITY_NORMAL | 4 | ||
THREAD_PRIORITY_ABOVE_NORMAL | 5 | ||
THREAD_PRIORITY_HIGHEST | 6 | ||
THREAD_PRIORITY_TIME_CRITICAL | 15 | ||
BELOW_NORMAL_PRIORITY_CLASS | THREAD_PRIORITY_IDLE | 1 | |
THREAD_PRIORITY_LOWEST | 4 | ||
THREAD_PRIORITY_BELOW_NORMAL | 5 | ||
THREAD_PRIORITY_NORMAL | 6 | ||
THREAD_PRIORITY_ABOVE_NORMAL | 7 | ||
THREAD_PRIORITY_HIGHEST | 8 | ||
THREAD_PRIORITY_TIME_CRITICAL | 15 | ||
NORMAL_PRIORITY_CLASS | THREAD_PRIORITY_IDLE | 1 | |
THREAD_PRIORITY_LOWEST | 6 | ||
THREAD_PRIORITY_BELOW_NORMAL | 7 | ||
THREAD_PRIORITY_NORMAL | 8 | ||
THREAD_PRIORITY_ABOVE_NORMAL | 9 | ||
THREAD_PRIORITY_HIGHEST | 10 | ||
THREAD_PRIORITY_TIME_CRITICAL | 15 | ||
ABOVE_NORMAL_PRIORITY_CLASS | THREAD_PRIORITY_IDLE | 1 | |
THREAD_PRIORITY_LOWEST | 8 | ||
THREAD_PRIORITY_BELOW_NORMAL | 9 | ||
THREAD_PRIORITY_NORMAL | 10 | ||
THREAD_PRIORITY_ABOVE_NORMAL | 11 | ||
THREAD_PRIORITY_HIGHEST | 12 | ||
THREAD_PRIORITY_TIME_CRITICAL | 15 | ||
HIGH_PRIORITY_CLASS | THREAD_PRIORITY_IDLE | 1 | |
THREAD_PRIORITY_LOWEST | 11 | ||
THREAD_PRIORITY_BELOW_NORMAL | 12 | ||
THREAD_PRIORITY_NORMAL | 13 | ||
THREAD_PRIORITY_ABOVE_NORMAL | 14 | ||
THREAD_PRIORITY_HIGHEST | 15 | ||
THREAD_PRIORITY_TIME_CRITICAL | 15 | ||
REALTIME_PRIORITY_CLASS | THREAD_PRIORITY_IDLE | 16 | |
THREAD_PRIORITY_LOWEST | 22 | ||
THREAD_PRIORITY_BELOW_NORMAL | 23 | ||
THREAD_PRIORITY_NORMAL | 24 | ||
THREAD_PRIORITY_ABOVE_NORMAL | 25 | ||
THREAD_PRIORITY_HIGHEST | 26 | ||
THREAD_PRIORITY_TIME_CRITICAL | 31 |