Thread vs ThreadPool



в чем разница между использованием нового потока и использует поток из пула потоков? Какие преимущества существуют и для чего поток из пула, а не одна я явно создал? Я думаю конкретно о .NET здесь, но общие примеры прекрасны.

1059   10  

10 ответов:

пул потоков обеспечит преимущества для частых и относительно коротких операций по

  • повторное использование уже созданных потоков вместо создания новых (дорогостоящий процесс)
  • дросселирование скорости создания потока, когда есть пакет запросов для новых рабочих элементов (я считаю, что это только в .NET 3.5)

    • Если вы ставите в очередь 100 задач пула потоков, он будет использовать только столько потоков, сколько уже было создан для обслуживания этих запросов (например, 10). Пул потоков будет часто проверять (я считаю, что каждые 500 мс в 3.5 SP1), и если есть задачи в очереди, он сделает один новый поток. Если ваши задачи быстры, то количество новых потоков будет небольшим, и повторное использование 10 или около того потоков для коротких задач будет быстрее, чем создание 100 потоков спереди.

    • Если ваша рабочая нагрузка постоянно имеет большое количество запросов пула потоков, то поток пул настроится на вашу рабочую нагрузку, создав больше потоков в пуле с помощью вышеуказанного процесса, чтобы было доступно большее количество потоков для обработки запросов

    • Регистрация здесь для более подробной информации о том, как работает пул потоков под капотом

создание нового потока самостоятельно было бы более уместным, если бы задание было относительно длительным (вероятно, около секунды или двух, но это зависит от конкретной ситуации)

@Krzysztof - потоки пула потоков являются фоновыми потоками, которые останавливаются, когда заканчивается основной поток. Созданные вручную потоки по умолчанию находятся на переднем плане (будут продолжать работать после завершения основного потока), но могут быть установлены в фоновом режиме перед вызовом Start на них.

интернет .Net управляемого класса ThreadPool: -

  • размеры сам на основе текущей рабочей нагрузки и доступного оборудования
  • содержит рабочие потоки и потоки портов завершения (которые специально используются для обслуживания ввода-вывода)
  • оптимизирован для большого количества относительно недолговечных операций

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

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

Итак, если вы создадите небольшое, ограниченное количество потоков, создайте их сами. Если вы не можете определить заранее, сколько потоков может быть создано (например они создаются в ответ на входящий IO), и их работа будет недолгой, используйте threadpool. Если вы не знаете, сколько, но их работа будет длительной, в платформе нет ничего, чтобы помочь вам, но вы можете найти альтернативные реализации threadpool, которые подходят.

и

new Thread().Start()

порождает поток переднего плана, который не умрет, если вы закроете свою программу. Потоки ThreadPool-это фоновые потоки, которые умирают при закрытии приложения.

Я был любопытен об относительном использовании ресурсов для них и запустил тест на своем двухъядерном ноутбуке Intel i5 2012 года с использованием .net 4.0 release build на windows 8. Пулы потоков занимали в среднем 0,035 мс для запуска, где потоки занимали в среднем 5,06 МС.другими словами, поток в пуле начинался примерно в 300 раз быстрее для большого количества короткоживущих потоков. По крайней мере, в тестируемом диапазоне (100-2000) потоков общее время на поток казалось довольно постоянным.

этот код это был бенчмаркинг:

    for (int i = 0; i < ThreadCount; i++) {
        Task.Run(() => { });
    }

    for (int i = 0; i < ThreadCount; i++) {
        var t = new Thread(() => { });
        t.Start();
    }

enter image description here

проверьте здесь для более ранней теме:

когда я не должен использовать ThreadPool в .Net?

резюме заключается в том, что Threadpool хорош, если вам нужно создать много короткоживущих потоков, тогда как использование потоков дает вам немного больше контроля.

локальное хранилище потоков-это не очень хорошая идея с пулами потоков. Это дает потокам "идентичность"; не все потоки равны больше. Теперь пулы потоков особенно полезны, если вам просто нужна куча одинаковых потоков, готовых выполнять вашу работу без накладных расходов на создание.

Если вам нужно много потоков, вы, вероятно, хотите использовать ThreadPool. Они повторно используют потоки, экономя накладные расходы на создание потоков.

Если вам просто нужен один поток, чтобы что-то сделать, поток, вероятно, проще всего.

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

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

Если нельзя ожидать, что метод выйдет в течение 100 мс или около того, когда он начнет выполнение, метод должен быть выполнен с помощью некоторых средств, отличных от основного пула потоков. Если у вас есть много задач для выполнения, которые являются интенсивными для процессора, но не блокируются, может быть полезно отправить их с помощью пула потоков приложений (по одному на ядро процессора), который является отдельно от" основного " пула потоков, поскольку использование большего количества потоков, чем ядра, будет контрпродуктивным при выполнении неблокирующих задач с интенсивным ЦП. Если, однако, метод займет секунду или больше времени для выполнения и будет тратить большую часть своего времени заблокирован, метод, вероятно, должен выполняться в выделенном потоке и почти наверняка не должен выполняться в потоке основного потока. Если длительная операция должна быть вызвана чем-то вроде обратного вызова ввода-вывода, следует либо запустить поток для длительная операция перед обратным вызовом и ее ожидание на мониторе, который импульсы обратного вызова, или же обратный вызов запускают новый поток для выполнения операции, когда обратный вызов завершается, эффективно возвращая свой собственный поток в пул потоков.

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

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

пример ограничения: У меня есть только 10 подключений к БД, поэтому я бы разрешил только 10 рабочих потоков для доступа к базе данных.

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

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

просто есть проблема с формой, использующей поток для обновления некоторого поля из базы данных на событии positionchanged элемента управления списком (избегайте freez). Это заняло 5 минут для моего пользователя, чтобы иметь ошибку из базы данных (слишком много связи с доступом), потому что он менял позицию списка слишком быстро...

Я знаю, что есть другой способ решить базовые проблемы (в том числе не используя доступ) , но объединение-хорошее начало.

Comments

    Ничего не найдено.