Russian Qt Forum
Март 29, 2024, 08:52 *
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
Вам не пришло письмо с кодом активации?

Войти
 
  Начало   Форум  WIKI (Вики)FAQ Помощь Поиск Войти Регистрация  

Страниц: 1 2 [3] 4 5 ... 8   Вниз
  Печать  
Автор Тема: Очереди, самодельные сигналы  (Прочитано 71119 раз)
galilley
Гость
« Ответ #30 : Август 12, 2010, 12:45 »

Самый простой способ: запустить нитку, она начнет крутить  свой eventLoop. Когда для нитки есть работа - послать ей сигнал. Нитка выполнит задание, вернет результаты (также через сигнал) и опять уйдет в eventLoop. Для этого в Qt все заточено, дополнительные семафоры не нужны. Просто создавайте и связывайте слоты/сигналы

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

Записан
Авварон
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 3257


Просмотр профиля
« Ответ #31 : Август 12, 2010, 12:48 »

это асинхронность...
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #32 : Август 12, 2010, 12:53 »

Но насколько я понял event loop всегда относится к главному потоку и в Qthread не поддерживается.
Или я ошибаюсь?
Ошибаетесь. Метод exec() (он стоит в run() по умолчанию) запускает eventLoop этой нитки
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #33 : Август 12, 2010, 13:02 »

Это всё понятно, но мне как раз нужда была синхронность, чтобы я мог, например, послать задание во вторичный поток, потом ещё что-нить сделать по ходу в первичном, потом дождаться ответа и выполнять программу дальше.
А Вас никто не заставляет ждать пока задание выполнится. Делайте коннект QueuedConnection и управление вернется после того как задание помещено в очередь нитки. А хотите ждать - используйте BlockingQueuedConnection
Записан
labview
Гость
« Ответ #34 : Август 12, 2010, 13:04 »

Но насколько я понял event loop всегда относится к главному потоку и в Qthread не поддерживается.
Или я ошибаюсь?
Ошибаетесь. Метод exec() (он стоит в run() по умолчанию) запускает eventLoop этой нитки

Да, я попутал, где то прочитал, что в Qt за User Interface всегда отвечает Main, и спутал это с за Event Loop всегда отвечает Main.
То есть в нитях нельзя создавать свои пользовательские окна.

Да, я согласен с тем, что система сигналов и слотов реализована достаточно хорошо. Но мне бы хотелось иметь прямой доступ к Thread, а не через его Event Loop, понимаете?
Ещё мне бы хотелось, раз уж такой возможности нет?!, сбрасывать сигналы (то есть делать их недействительными), если нить их например не может обработать. А так же иметь возможность указать максимальное количество сигналов (размер буфера) для Event Loop определённой нити. И ещё менять сигналы местами или добавлять сигналы не в конец буфера, а в начало например.

Блин, во время написания этого ответа вспомнился момент из камеди клаба:
http://video.google.com/videoplay?docid=4145626155888365960#
Записан
galilley
Гость
« Ответ #35 : Август 12, 2010, 13:30 »

А Вас никто не заставляет ждать пока задание выполнится. Делайте коннект QueuedConnection и управление вернется после того как задание помещено в очередь нитки. А хотите ждать - используйте BlockingQueuedConnection

Но я хотел бы ещё ту же получить ответ из вторичного треда.. хотя да, ответ можно спросить и напрямую, дождавшись пока отработает BlockingQueuedConnection. Надо подумать над этим, спасибо Улыбающийся

Да, я согласен с тем, что система сигналов и слотов реализована достаточно хорошо. Но мне бы хотелось иметь прямой доступ к Thread, а не через его Event Loop, понимаете?
Ещё мне бы хотелось, раз уж такой возможности нет?!, сбрасывать сигналы (то есть делать их недействительными), если нить их например не может обработать. А так же иметь возможность указать максимальное количество сигналов (размер буфера) для Event Loop определённой нити. И ещё менять сигналы местами или добавлять сигналы не в конец буфера, а в начало например.
А что за задача, если не секрет? Может там надо решать проблему другими способами, или с другого угла.. да и крайне интересны условия, в которых могли возникнуть такие потребности.
« Последнее редактирование: Август 12, 2010, 13:32 от galilley » Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #36 : Август 12, 2010, 13:50 »

Но я хотел бы ещё ту же получить ответ из вторичного треда.. хотя да, ответ можно спросить и напрямую, дождавшись пока отработает BlockingQueuedConnection.
Случай когда надо ждать ответа - довольно редкий. В большинстве случаев ответ посылается из нитки выполнившей задание (тоже сигналом) и принимается в eventLoop главной (или др) нитки.  Др. словами гораздо удобнее "ждать с пользой" в eventLoop
Записан
BRE
Гость
« Ответ #37 : Август 12, 2010, 14:00 »

IMHO стоит взглянуть на QRunnable + QThreadPool.
eventloop в простаивающей нитке все равно кушает процессор и чем больше таких ниток, тем больше кушает.
Записан
labview
Гость
« Ответ #38 : Август 12, 2010, 14:10 »

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

Ну во первых я не очень понимаю зачем каждой нити свой Event Loop, то есть каждая нить состоит из двух потоков - Event Loop + сам цикл нити. Наверняка как то можно передавать данные напрямую и синхронно в цикл нити, не используя Event Loop.

Во вторых нить например должна отправлять данные какому нибудь внешнему прибору. Допустим данные имеют разный приоритет. Для примера команда exit имеет высший приоритет, а если в данный момент в буфере Event Loop уже находятся другие команды низкого приоритета, то мне бы хотелось убрать команды низкого приоритета из буфера сигналов и сразу выполнить сигнал высокого приоритета. Ну или просто всунуть команду высокого приоритета в буфер на первое место, а остальные подождут.

Ну примерно понятно?
Записан
BRE
Гость
« Ответ #39 : Август 12, 2010, 14:17 »

Сделать свою очередь заданий будет самое то.
Кстати на форуме были темы, где выкладывались готовые рабочие примеры организации таких задач.
Так же можно посмотреть реализацию QRunnable и QThreadPool.
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #40 : Август 12, 2010, 14:26 »

Да, я согласен с тем, что система сигналов и слотов реализована достаточно хорошо. Но мне бы хотелось иметь прямой доступ к Thread, а не через его Event Loop, понимаете?
Думаю что понимаю Улыбающийся Но, судя по тому что Вы рассказали, никакой необходимости в этом не видно
Ещё мне бы хотелось, раз уж такой возможности нет?!, сбрасывать сигналы (то есть делать их недействительными), если нить их например не может обработать. А так же иметь возможность указать максимальное количество сигналов (размер буфера) для Event Loop определённой нити. И ещё менять сигналы местами или добавлять сигналы не в конец буфера, а в начало например.
Мне кажется Вы путаете синхронное с асинхронным  Улыбающийся Сигнал всего лишь "посылает нитке задание". На посылающей стороне как правило нет выбора - задачи посылаются исполняющей нитке в порядке их поступления. Но исполнитель совсем не обязан следовать тому же порядку. В любой момент он может вызвать processEvents и посмотреть какие еще задачи пришли, прервать выполнение текущей задачи, установить свой порядок выполнения задач и.т.п.
Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #41 : Август 12, 2010, 14:33 »

eventloop в простаивающей нитке все равно кушает процессор и чем больше таких ниток, тем больше кушает.
Вряд ли. Запускаем любую Qt программу которая открывает UI и ждет ввода пользователя (т.е. стоит на eventLoop). Активность процессора (ов) на нуле.
Записан
BRE
Гость
« Ответ #42 : Август 12, 2010, 14:38 »

Вряд ли. Запускаем любую Qt программу которая открывает UI и ждет ввода пользователя (т.е. стоит на eventLoop). Активность процессора (ов) на нуле.
Что значит вряд ли.  Улыбающийся Если посмотреть реализацию, то на каждой итерации, помимо обработки самих событий, происходит еще масса разных действий. И все это будет выполняться во всех таких нитках без всякой нужды.

Записан
Igors
Джедай : наставник для всех
*******
Offline Offline

Сообщений: 11445


Просмотр профиля
« Ответ #43 : Август 12, 2010, 14:45 »

Ну во первых я не очень понимаю зачем каждой нити свой Event Loop, то есть каждая нить состоит из двух потоков - Event Loop + сам цикл нити. Наверняка как то можно передавать данные напрямую и синхронно в цикл нити, не используя Event Loop.
Когда ОС запускает нитку, дается ф-ция которую эта нитка начнет выполнять. Как только ф-ция вернет управление - нитка завершена. Qt по умолчанию запускает eventLoop. Вы можете вместо этого сделать свой цикл нитки (обычно не очень удобно), можете войти в eventLoop, выйти, опять войти - как угодно но все в пределах run() нитки.

Стандартная проблема с собственным циклом - нитке нужно ждать пока данных для обработки нет и нужно как-то сниматься с ожидания когда данные пришли. Во многих случаях выходит то же самое что делает eventLoop
Записан
BRE
Гость
« Ответ #44 : Август 12, 2010, 14:51 »

Стандартная проблема с собственным циклом - нитке нужно ждать пока данных для обработки нет и нужно как-то сниматься с ожидания когда данные пришли. Во многих случаях выходит то же самое что делает eventLoop
А в чем эта проблема?
Нитка останавливается на объекте QWaitCondition::wait, когда задание добавляется, то делаем QWaitCondition::wakeOne и одна из ниток просыпается и подхватывает задание.
Записан
Страниц: 1 2 [3] 4 5 ... 8   Вверх
  Печать  
 
Перейти в:  


Страница сгенерирована за 0.058 секунд. Запросов: 23.