| Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате |
| Форум программистов > Visual C++/MFC/WTL > Thread - как остановить? |
| Автор: Nuzur 12.1.2005, 20:05 |
| Я создаю поток HCOM1 = AfxBeginThread(COM1, this); как потом его остановиьть чтобы неюыло ликов? Поток должен выполняться на протяжении всей роботы программы. |
| Автор: Coocky 12.1.2005, 22:11 |
| Неь,нужно прописать что-то типа AutoDelete///Короче посмотрю,а то не помню...Ну если раньше не ответят.. Вообще-то посмотри МСДН про потоки в МФС там есть |
| Автор: S.A.P. 12.1.2005, 22:59 |
| Что у тебя означает COM1. По идее это должен быть объект - наследник класса CWinThread, тогда глюков быть не должно. |
| Автор: En_t_end 13.1.2005, 06:52 |
| А глюки будут, так как с этого дня ты узреешь, что в С++ надо обязательно уничтожать обьекты памяти, особенно при работе с потоками и при их многоразовом использовании Вот это ссылка тебе возможно поможет : http://forum.vingrad.ru/index.php?showtopic=38847 А вообще тебе надо именно приостановить ?(для таких случаев имхо suspendthread смотри) или остановить, поменять значения для потока, а потом запустить ? - вот если так, то по той ссылке тебе обязательно надо сходить! |
| Автор: Nuzur 13.1.2005, 17:29 |
| Фунция, простите поток, обьявлен у меня так Добавлено @ 17:33 Фунция, простите поток, обьявлен у меня так UINT Stream(LPVOID Param) Дело в том что он должен просматривать очередь и если она не пуста то выполнять там определенные действий, а при закрытии программы вызываеться деструктор очередь, ну и должен закрыться поток. |
| Автор: S.A.P. 13.1.2005, 17:43 | ||
| Какой смысл тебе использовать MFC функции, когда та не создаешь объект класса CWinThread?. Делай на API, вот пример:
|
| Автор: En_t_end 13.1.2005, 19:16 |
| Да WinApi в этом случае будет актуальнее... |
| Автор: alien_by 14.1.2005, 18:38 |
| Хорошо зарекомендовал себя след способ В класе своего трида (например СMyThread) обьявляешь, например, метод ReleaseThread. void CMyThread::ReleaseThread(int nExitCode) { PostThreadMessage(WM_QUIT, nExitCode, NULL); } ну а когда поток надо кикнуть, вызываешь данный метод. Работает на ура. |
| Автор: En_t_end 14.1.2005, 18:40 |
| alien_by Всё гениальное просто ! |
| Автор: Adil' 15.1.2005, 12:56 | ||
А просто
|
| Автор: Nuzur 15.1.2005, 15:27 |
| DWORD WINAPI Наверное вы правы, так действительно будет лучше, но лик всеравно остался, правда меньше 100 бай, но это вопрос принцыпа. Может там проблема в самой функции? Она организована так: DWORD WINAPI COM1(LPVOID Param) { while(true) { ..... Sleep(delay); }; return 0; } Идем дальше, void CMyThread::ReleaseThread(int nExitCode) { PostThreadMessage(WM_QUIT, nExitCode, NULL); } ничего не сработало |
| Автор: S.A.P. 15.1.2005, 23:30 |
| Nuzur мой способ возьми. |
| Автор: Adil' 16.1.2005, 12:12 | ||
| Если на WinApi (точнее, не используя CWinThread), то PostThreadMessage не будет работать до тех пор, пока в процедуру потока не будет вставлена соответствующая обработка сообщений виндов (GetMessage или PeekMessage). Сделай лучше
|
| Автор: Goldberg 29.1.2005, 18:07 |
| Если будешь использовать CWinThread, то: BEGIN_MESSAGE_MAP(CTvoiPotok, CWinThread) ON_THREAD_MESSAGE(WM_TO_THREAD, OnWMToThread) END_MESSAGE_MAP() В InitInstance() своего потока вызывай Run(). Ну и потом шлешь сообщения: PostThreadMessage(TvoiPotok.m_nThreadID, WM_TO_THREAD, 0, 0); |
| Автор: Coocky 11.2.2005, 22:51 |
| Че-то я проморозился и морозиться продолжаю Ну ладно,пора браться за старое alien_by А если не работаю с производным классом от СWinThread? Вообще для остановки потока я знаю три способа: 1.Остановка с помощю задание флага,используя глобальную переменную(примитивно и неактуально) 2.Способ предложеный(похожий) на alien_by,с помощью отправки своего сообщения. 3.С помощью класса CEvent. Если еще интересно ответь,я напишу с примерами. |
| Автор: Nuzur 13.2.2005, 14:40 | ||
Интерестно, в данном проекте уже вроде как-то прокатило и с ликом, но в жизни пригодиться это точно. Тоесть если вам не сложно, то я буду очень признателен |
| Автор: Nuzur 22.2.2005, 17:36 |
| Ну так где там примеры? Мне ведь интерестно! |
| Автор: Coocky 22.2.2005, 20:02 |
| Секунду Nuzur,ща горю...Курсовая... |
| Автор: Nuzur 11.3.2005, 20:09 |
| Последний раз поднимаю. |
| Автор: Coocky 11.3.2005, 22:55 |
| Nuzur Завтра,гадом буду |
| Автор: bel_nikita 11.3.2005, 23:41 | ||
А можно послать MFC и утворить:
|
| Автор: Coocky 11.3.2005, 23:43 |
| bel_nikita,не понял.Это насчет переменной? Добавлено @ 23:44 А ,все понятно...Но вижу только 2 способа.А че МФС посылать? |
| Автор: bel_nikita 11.3.2005, 23:56 | ||
Coocky
А потому, что я его не знаю З.Ы.: А вообще, треды функциями, типа WaitForSingleObject ..., останавливают |
| Автор: Coocky 12.3.2005, 00:00 | ||
Да,и это считается нормальным и правильным!Но есть и другие методы-иногда похабные,но простые.Короче завтра напишу-если че прочтешь:-) |
| Автор: Coocky 12.3.2005, 23:25 | ||||
| Итак,как обещал 1 Способ-глобальные переменные.Не лучший способ-небезопасен. Итак заводим перемную,КОТОРУЮ добавлем вверху,сразу после endif; Обьявляем ее так votalite bool Stop;(votalite-это означает,что вне потока!) Присваиваем ей значение Stop=true; И теперь в функции потока (MyPotok() ;) пишем
//Когда нужно остановить-пишем Stop=false; //Все 2 Способ тебе описали -это с помощью сообщения.Повторятся не буду. 3 Способ.CEvent Создаем глобальные обьекты CEvent Start и CEvent Stop ; Добавляем #include "afxmt.h" Для установки в состояние сигнализации делаем Start.SetEvent(); Stop.SetEvent();(там где раньше true и false) и теперь функция
Все понятно или обьяснить.Если не поймешь что к чему,пиши -обьясню на пальцах |
| Автор: Coocky 12.3.2005, 23:39 |
| Да, добавлю.Последний способ-єто сигнализация обьекта CEvent. Когда Start переведется в состоянии сигнализации,функция начнет работать. Поток входит в цикл while,где віполняется опрос обьекта собітия Stop.Цикл продолжается до тех пор,потка обьект Stop не будет переведен в состояние сигнализации,и выйдем. Извини,че не так с синтаксисом-пишу с головы и в плохом состоянии Если че не так исправлю.Когда протрезвею Удачи.Побежал |
| Автор: Олег М 14.3.2005, 22:03 | ||
| Coocky, Идея здесь уже была написана, просто повторю. Поток - это цикл (в общем случае), поэтому, если не нужно использовать CWinThread, а его им лучше пользоваться только когда потоку необходимо передавать сообщения типа SenMessage (чем лично я никогда не пользовался - не было нужды), все делают так
Объявляем глобальную, по отношению к функции потока, переменную и зацикливаем поток до тех пор, пока кто-то не изменит её значение (остановит поток). Так как поток в основном ждёт чего-то (WaitFor....Object), то такой цикл не будет занимать много процессорного времени. Функцию Sleep лучше не использовать, потому что из неё невозможно корректно выйти, без TerminateThread. |
| Автор: Coocky 15.3.2005, 14:05 | ||
| Олег М Я не понял твоей иронии.Я человеку показываю все доступные методы,а его выбор,чем пользоваться
Зачем-ЧТО? Nuzur И еще.Во всех приведеных примерах ты посылал ПОТОКУ команду из главной проги,когда остановиться. Но есть ситуация,когда ПОТОК должен сказать проге,что мне пора бы остановиться.Для этого регистрируешь свое сообщение,и когда поток должен сказать-все хватит,отправляешь из него это сообщение.А в обработчике своего сообщения ставишь обьекты или переменные в нужное состояние.И все происходит как выше... |
| Автор: Олег М 15.3.2005, 14:58 | ||
Зачем использовать событие в качестве булевской переменной |
| Автор: Coocky 16.3.2005, 14:21 | ||
Олег М
А что в этом плохого? Нормальный подход..А чем он хуже твоего? |
| Автор: Tneiro 17.3.2005, 16:56 |
| 1 CWinThread::SuspendThread()-приостановка потока CWinThread::ResumeThread()-возобновление 2 ::Sleep() завершение потока 1 AfxEndThread или API PostQuitMessage c флагом WM_QUIT если поток отправляет сообшение сам себе 2 GetExitCodeThread() |
| Автор: Олег М 17.3.2005, 21:01 | ||
Нормального немного, как-то слишком хитро и медленно. Единственно, что одно событие можно использовать в разных процессах. Но это, я так понял, в данном случае не актуально. Вот что действительно нужно, так это использовать WaitForSingleObject для события вместо Sleep. Потому что при необходимости корректно завершить поток Sleep нельзя прервать, а ожидание события можно. |