Если 256 потоков дают лучшую производительность, чем 8, вероятно, я ошибся? - PullRequest
2 голосов
/ 11 января 2010

Я только начал программировать с потоками POSIX в двухъядерной системе x86_64 Linux. Кажется, что 256 потоков - это почти оптимальная производительность, как я это сделал. Мне интересно, как это может быть? И может ли это означать, что мой подход неверен и лучший подход потребует гораздо меньшего количества потоков и будет таким же быстрым или быстрым?

Для получения дополнительной информации (рассматриваемая программа является каркасом для многопоточного генератора изображений с М-набором), см. Следующие вопросы, которые я уже задавал:

Используя потоки, как мне поступить с тем, что в идеале должно происходить в последовательном порядке?

Как мое приложение для создания потоковых изображений может передавать данные в графический интерфейс?

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

Таким образом, если 256 потоков, работающих быстрее, чем 8 потоков, не свидетельствуют о плохом подходе к созданию потоков, почему 256 потоков превосходят 8 потоков?

Тест для проверки скорости является частью набора Мандельброта , расположенного по адресу:

xmin -0.76243636067708333333333328
xmax -0.7624335575810185185185186
ymax 0.077996663411458333333333929

рассчитано максимум до 30000 итераций.

В версии без потоков время рендеринга в моей системе составляет около 15 секунд. В многопоточной версии средняя скорость для 8 потоков составляет 7,8 секунды, а для 256 потоков - 7,6 секунды.

Ответы [ 5 ]

4 голосов
/ 11 января 2010

Ну, наверное, да, вы делаете что-то не так.

Однако существуют обстоятельства, при которых 256 потоков будут работать лучше, чем 8, и при этом у вас не обязательно будет плохая модель потоков. Следует помнить, что наличие 8 потоков не означает, что все 8 потоков фактически работают все время. Каждый раз, когда один поток выполняет системный вызов блокировки для операционной системы, поток прекращает работу и ожидает результата. Между тем, другой поток часто может работать.

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

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

2 голосов
/ 11 января 2010

Может ли ваше приложение быть связанным? Как генерируются данные изображения?

1 голос
/ 11 января 2010

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

Если вы наблюдаете улучшение производительности вплоть до 256 потоков, я бы хотел сказать, что у вас где-то есть серьезное узкое место в производительности, и это не ЦП. Чтобы проверить это, попробуйте посмотреть, можете ли вы измерить время простоя отдельных потоков. Я подозреваю, что вы увидите, что ваши потоки застревают в состоянии «заблокировано» или «ожидают» на более длительный период своей жизни, чем они проводят в состоянии «работает» или «активно». Некоторые отладчики или инструменты профилирования функций позволят вам сделать это, и я думаю, что есть и инструменты Linux, которые делают это в командной строке.

1 голос
/ 11 января 2010

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

1 голос
/ 11 января 2010

Улучшение производительности, полученное благодаря выделению большего количества потоков, чем ядер, свидетельствует о том, что ЦП не является узким местом. Если речь идет о доступе ввода-вывода, таком как доступ к диску, памяти или даже сети, ваши результаты имеют смысл.

...