(?) Класс + Многопоточность
Модераторы: Hawk, Romeo, Absurd, DeeJayC, WinMain
Привет всем.
У меня проблема, о ней ниже.
Цель:
Необходимо создать класс, который при своей инициализации (с помощью
коструктора) создавал бы поток, который в свою очередь мог бы иметь доступ к
члена класса, в котором он создан.
Код(упрощенный) такой:
class Ms
{
public:
Ms();
HANDLE heExit;
unsigned int WINAPI Rt(PVOID pvParam);
private:
HANDLE htRt;
};
Ms::Ms()
{
unsigned threadID;
heExit = CreateEvent(NULL, TRUE, FALSE, NULL);
htRt = (HANDLE)_beginthreadex( NULL, 0, &Rt, NULL, 0, &threadID ); // (?)
}
Проблема:
Компилятор ругается error C2276: '&' : illegal operation on bound member
function expression.
но если поставить в определении класса вместо unsigned int WINAPI Rt(PVOID
pvParam); поставить static unsigned int WINAPI Rt(PVOID pvParam); то
_beginthreadex спокойно это переваривает. Но мне не нужна статическая
функция - она не может получить доступ к нестатическим членам класса.
Спасибо.
У меня проблема, о ней ниже.
Цель:
Необходимо создать класс, который при своей инициализации (с помощью
коструктора) создавал бы поток, который в свою очередь мог бы иметь доступ к
члена класса, в котором он создан.
Код(упрощенный) такой:
class Ms
{
public:
Ms();
HANDLE heExit;
unsigned int WINAPI Rt(PVOID pvParam);
private:
HANDLE htRt;
};
Ms::Ms()
{
unsigned threadID;
heExit = CreateEvent(NULL, TRUE, FALSE, NULL);
htRt = (HANDLE)_beginthreadex( NULL, 0, &Rt, NULL, 0, &threadID ); // (?)
}
Проблема:
Компилятор ругается error C2276: '&' : illegal operation on bound member
function expression.
но если поставить в определении класса вместо unsigned int WINAPI Rt(PVOID
pvParam); поставить static unsigned int WINAPI Rt(PVOID pvParam); то
_beginthreadex спокойно это переваривает. Но мне не нужна статическая
функция - она не может получить доступ к нестатическим членам класса.
Спасибо.
-
- Сообщения: 1228
- Зарегистрирован: 26 фев 2004, 13:24
- Откуда: Pietari, Venäjä
- Контактная информация:
Надо просунуть указатель this через параметр callback - функции.
htRt = (HANDLE)_beginthreadex( NULL, 0, &threadFunc, this, 0, &threadID );
//.....
static unsigned int __stdcall threadFunc(void* pvParam) {
Ms *this__ = static_cast<Ms *>(pvParam);
return this__->Rt();
}
htRt = (HANDLE)_beginthreadex( NULL, 0, &threadFunc, this, 0, &threadID );
//.....
static unsigned int __stdcall threadFunc(void* pvParam) {
Ms *this__ = static_cast<Ms *>(pvParam);
return this__->Rt();
}
2B OR NOT(2B) = FF
Непомогает, пишет всё тоже:
error C2276: '&' : illegal operation on bound member function expression
error C2276: '&' : illegal operation on bound member function expression
- Romeo
- Сообщения: 3126
- Зарегистрирован: 02 мар 2004, 17:25
- Откуда: Крым, Севастополь
- Контактная информация:
Наверное ты забыл вместо Rt в вызове _beginthreadex, написать threadFunc. Других причин столь странного поведения не вижу.
Entites should not be multiplied beyond necessity @ William Occam
---
Для выделения С++ кода используйте конструкцию [ code=cpp ] Код [ /code ] (без пробелов)
---
Сообщение "Спасибо" малоинформативно. Благодарность правильнее высказать, воспользовавшись кнопкой "Reputation" в виде звёздочки, расположенной в левом нижнем углу рамки сообщения.
---
Для выделения С++ кода используйте конструкцию [ code=cpp ] Код [ /code ] (без пробелов)
---
Сообщение "Спасибо" малоинформативно. Благодарность правильнее высказать, воспользовавшись кнопкой "Reputation" в виде звёздочки, расположенной в левом нижнем углу рамки сообщения.
Посмотри, как я делал:
Код: Выделить всё
#include "MyDlgClass.h"
// Эта функция выполняется в отдельном потоке...
unsigned __stdcall DlgConfigFunc(void *v)
{
if (!v) return 0;
((CMyDlgClass*)v)->UpdateDlgConfig();
return 1;
}
// Обработчик какого-то события в окне диалога...
LRESULT CMyDlgClass::OnDlgEventResponse(<список аргументов>)
{
_beginthreadex(NULL, 0, DlgConfigFunc, this, 0, NULL);
return 0;
}
void CMyDlgClass::UpdateDlgConfig()
{
// Какой-то код...
}
-
- Сообщения: 1228
- Зарегистрирован: 26 фев 2004, 13:24
- Откуда: Pietari, Venäjä
- Контактная информация:
Вообще-то говоря желательно пользоваться имеющимися тредами вместо порождения новых:
unsigned __stdcall DlgConfigFunc(void *v)
{
do {
if(WaitForSingleObject(hEvent, INFINITE) != WAIT_OBJECT_0 || endFlag) { break; }
((CMyDlgClass*)v)->UpdateDlgConfig();
} while (1);
return 0;
}
LRESULT CMyDlgClass::OnDlgEventResponse(<список аргументов>)
{
SetEvent(hEvent);
return 0;
}
unsigned __stdcall DlgConfigFunc(void *v)
{
do {
if(WaitForSingleObject(hEvent, INFINITE) != WAIT_OBJECT_0 || endFlag) { break; }
((CMyDlgClass*)v)->UpdateDlgConfig();
} while (1);
return 0;
}
LRESULT CMyDlgClass::OnDlgEventResponse(<список аргументов>)
{
SetEvent(hEvent);
return 0;
}
2B OR NOT(2B) = FF
Спасибо. Этот прием мне помог. С помощью него можно решить задачу мою.#include "MyDlgClass.h"
// Эта функция выполняется в отдельном потоке...
unsigned __stdcall DlgConfigFunc(void *v)
{
if (!v) return 0;
((CMyDlgClass*)v)->UpdateDlgConfig();
return 1;
}
// Обработчик какого-то события в окне диалога...
LRESULT CMyDlgClass::OnDlgEventResponse(<список аргументов>)
{
_beginthreadex(NULL, 0, DlgConfigFunc, this, 0, NULL);
return 0;
}
void CMyDlgClass::UpdateDlgConfig()
{
// Какой-то код...
}
Но хотелось бы всетаки запускать функцию-член класса что бы было поменьше глобальных функций.
Нестатический метод класса НЕ МОЖЕТ быть функцией потока: у них разные сигнатуры, и что хуже, соглашения по вызову.Но хотелось бы всетаки запускать функцию-член класса что бы было поменьше глобальных функций.
Спасибо всем, помогли. Вопросов больше пока не имею.