powered by simpleCommunicator - 2.0.59     © 2025 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / C++ [игнор отключен] [закрыт для гостей] / Почему не распараллеливаются потоки
27 сообщений из 27, показаны все 2 страниц
Почему не распараллеливаются потоки
    #39356060
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Добрый день, коллеги!

Столкнулся с проблемой при распараллеливании вычислений, и не могу понять причину почему потоки не работают параллельно.
Пишу на с++ Builder 6 приложение. Пробовал и на dll перенести в VS 2008, итог одинаковый.

Для запуска в потока использую API Windows CreateThread, количество потоков контролирую семафорами. Отладил потоки сначала на простенькой функции сложения в цикле, поверил запустил все работает, потоки грузят ядра процессора. Как только перенес алгоритм расчета в поток, многопоточность перестала работать, точнее она вроде бы и есть но при работе грузится только 1 процессор.

В поточных расчете используется порядка 7 классов, и операции с данными в этих классах, обход деревьев, разделение деревьев, объединение деревьев, деревья реализованы на вектора std.

Может как то можно отловить кусок кода который препятствует распараллеливанию потоков?
Поделитесь опытом...
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356066
Dima T
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Логи пиши и изучай что каждый поток делает. ID потока GetCurrentThreadId()
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356081
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
GarfishДля запуска в потока использую API Windows CreateThread

"Уже смешно", доки явно не читаны.

GarfishМожет как то можно отловить кусок кода который препятствует
распараллеливанию потоков?
Профилер попробуй.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356177
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
GarfishДобрый день, коллеги!

Столкнулся с проблемой при распараллеливании вычислений, и не могу понять причину почему потоки не работают параллельно.
Пишу на с++ Builder 6 приложение. Пробовал и на dll перенести в VS 2008, итог одинаковый.
...

В поточных расчете используется порядка 7 классов, и операции с данными в этих классах, обход деревьев, разделение деревьев, объединение деревьев, деревья реализованы на вектора std.

Может как то можно отловить кусок кода который препятствует распараллеливанию потоков?
Поделитесь опытом...

Это всё очень сложно, и без кода вообще нет смысла обсуждать.
Скоре всего, всё тривиально, и ты просто неправильно диагносцируешь загрузку процессоров.
Но может быть и ты сделал какую-то сериализацию в программе, и потоки друг другу мешают.

Например, что значит вот это вот :
авторДля запуска в потока использую API Windows CreateThread, количество потоков контролирую семафорами. Отладил потоки
?

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


И в идеале это вообще не нужно делать, в идеале многопоточная программа должна выглядеть так:
0) взял всю работу, что нужно сделать, описал её данными.
1) разделил эту работу на куски в соответствии с уровнем параллелизма системы (N кусков)(грубо -- кол-во процессоров).
2) запустил N потоков, каждому из потоков дал свой кусок вычислений.
3) дождался конца выполнения каждого из потоков.
4) для хорошего распаралеливания нужно, чтобы у потоков не было общих выходных данных, а входные были бы только на
чтение. Иначе надо будет синхронизировать доступ к данным, что приведёт неизбежно к состязаниям за этот доступ и
снижению общего уровня параллелизма.
5) в конце все потоки должны отдать результаты и главный поток должен их как-то сагрегировать в единый результат.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356180
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Dimitry SibiryakovGarfishДля запуска в потока использую API Windows CreateThread

"Уже смешно", доки явно не читаны.


Ты на beginthread_ex намекаешь ?
Если так, не факт, что он в Builder е есть или если есть, то так же называется.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356218
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MasterZivТы на beginthread_ex намекаешь ?
Я намекаю на явное указание "никогда не использовать эту функцию в программах,
использующих RTL".
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356254
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MasterZiv,

по 4 пункту есть общая выходная переменная std::vector по окончании вычислений объем больше 1 гига, результаты всех потоков записываются в структуру и передаются в вектор

спасибо есть интересные идеи будем думать
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356366
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Dimitry SibiryakovMasterZivТы на beginthread_ex намекаешь ?
Я намекаю на явное указание "никогда не использовать эту функцию в программах,
использующих RTL".



ну это одно и то же.
на самом деле можно, если в этом созданном потоке CRT не использовать...
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356369
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfish,

тебе думать не надо, тебе надо код опубликовать, если хочешь, чтобы тебе помогли...
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356599
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MasterZiv,

сделал ведение лога по прохождению функции и записью Id процесса, процессы работают параллельно но в пределах одного ядра.
начал отключать куски кода, и нашел что распараллеливание пропадает при подключении сборки дерева на рекурсивном вызове new
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
void node::node(vector<csgjs_polygon> &list)
{
...
if (!front) front = new node(list_front);
if (!back) back= new node(list_back);
...
}


сли исходить из такой логики, что потоки работают в одном адресном пространстве программы, то работа с общей памятью при выделении памяти происходит в "одно окно"
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356762
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Запросто.

Есть многопоточные аллокаторы, но если ты хочешь быструю программу - старайся уйти от постоянных мелких выделений памяти.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39356777
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
GarfishMasterZiv,

сделал ведение лога по прохождению функции и записью Id процесса, процессы работают параллельно но в пределах одного ядра.
начал отключать куски кода, и нашел что распараллеливание пропадает при подключении сборки дерева на рекурсивном вызове new
Код: plaintext
1.
2.
3.
4.
5.
6.
7.
void node::node(vector<csgjs_polygon> &list)
{
...
if (!front) front = new node(list_front);
if (!back) back= new node(list_back);
...
}


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


сказки не рассказывай.

впрочем, если у тебя билдер, и там может ты собрал с однопоточной CRT, и она там сделана так, что на всякий случай ставит process affinity mask на один проц, то ты вполне можешь получить такую картину.

это все предположение, я билдер не знаю, и знаю не хочу, и тебе не советую.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357289
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MasterZiv,

проблема в new как я и предполагал, когда используется new работа с общим адресным пространством программы работает в одно окно, я сделал простенький проект с многопоточностью.
В нем 2 функции, Первая MulAdd1 без использования new, все распараллеливается на 4 ядра.
И вторая функция MulAdd2 где используется оператор new многопоточность исчезает.

посмотри пожалуйста, как можно распараллелить потоки по ядрам не изменяя код функции MulAdd2

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
DWORD WINAPI ThreadRoutine(LPVOID Param)
{
	HANDLE hSemaphore = OpenSemaphore( SEMAPHORE_ALL_ACCESS,0 ,lpSemaphoreName);//открываем семафор

  MulAdd1();//потоки грузят 4 ядра
 // MulAdd2();//работает в один поток
  
	ReleaseSemaphore(hSemaphore, 1, NULL);//освобождаем семафор
  CloseHandle(hSemaphore);
	ExitThread(0);
	return 0;
}
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357293
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfishкак можно распараллелить потоки по ядрам не изменяя код функции MulAdd2

Ну, например, можно переопределить операторы new и delete объектов, которые там
выделяются-освобождаются так, чтобы они были более thread-friendly.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357298
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Dimitry Sibiryakov,

а как?
new вызывается в конструкторе класса
delete в деструкторе

и принцип работы такой, что я обхожу по узлам деревья и строю новое node->node->node->node-> .... node->node->node->end

можно это решить как то за пределами функции использующей выделение памяти, что бы для каждого потока задать свое адресное пространство?
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357309
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Siemargl,

многопоточный аллокатор, как его сделать? ни разу не сталкивался, но похоже это то, что надо в моем случае
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357322
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfish,

Трай гуггл зис, Люк!
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357329
Фотография SashaMercury
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfish,

проблема может быть не в какой-то синтаксической ошибке или качестве вашего кода, а в том, что разработанная программа не реентерабельна в целом
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357332
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SashaMercury,

как в потоках реализовать разделяемое адресное пространство не знаю, но вот используя разделяемую память можно запустить разные процессы и читать данные в разделяемой памяти, процессы будет между собой изолированы на работу с памятью но будет общая точка обмена данными разделяемая память, пока что я вижу такую возможность распараллеливания
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357364
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfish,
что проще то выделить память до создания потока, передать в функцию потока, потом удалить?
можно также вообще память не выделять, использовать статическую память, Или выделять через alloca().
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357450
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
MasterZiv,

а применительно к конструктору node как это можно сделать?

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
void node::node(vector<csgjs_polygon> &list)
{
...
if (!front) front = new node(list_front);
if (!back) back= new node(list_back);
...
}
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357597
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfish,

я потом посмотрю всё, отпишусь...
сорри сейчас некогда...
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357602
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
GarfishMasterZiv,

а применительно к конструктору node как это можно сделать?

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
void node::node(vector<csgjs_polygon> &list)
{
...
if (!front) front = new node(list_front);
if (!back) back= new node(list_back);
...
}



в очередной раз прошу посылать ВЕСЬ код...
сделать то можно, вопрос, что дальше будет.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39357641
д0k
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
GarfishDimitry Sibiryakov,

а как?



Сюда смотри,
Ищи как можно добраться до нужных тебе системных вызовов из используемой тобой
обертки.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39358090
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
[quot Garfish]SashaMercury,

как в потоках реализовать разделяемое адресное пространство не знаю,

просто
0) выделить память
1) использовать только в этом потоке
2) вовремя удалить память

если использовать все виды стековой памяти , то вообще все автоматом разделяется.
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39361180
Фотография Garfish
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
распараллеливание получилось, проблему решил вышеуказанным методом.
всем спасибо!
...
Рейтинг: 0 / 0
Почему не распараллеливаются потоки
    #39361695
Фотография MasterZiv
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Garfishраспараллеливание получилось, проблему решил вышеуказанным методом.
всем спасибо!

Расскажи, что было то?
Affinity?
А откуда оно взялось?
...
Рейтинг: 0 / 0
27 сообщений из 27, показаны все 2 страниц
Форумы / C++ [игнор отключен] [закрыт для гостей] / Почему не распараллеливаются потоки
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]