Russian Qt Forum

Qt => Общие вопросы => Тема начата: QCasper от Июнь 05, 2006, 15:02



Название: доступ к переменным и объектам в QThread
Отправлено: QCasper от Июнь 05, 2006, 15:02
создаю поток как обычно наследую от QThread.

Код:
class mt : public QThread {
int i;
public:
     int v() {return i;}
     void run();
}

void mt::run() {
     i=10000;
     while(i) i--;
}


вопрос, могу ли я во время выполнения потока получить доступ к переменной i, посредством метода v() и считать ее значение?


Название: доступ к переменным и объектам в QThread
Отправлено: ElderOrb от Июнь 05, 2006, 15:21
Почему нет?.. Единственный нюанс - придётся обвешать эту переменную мьютексами..


Название: доступ к переменным и объектам в QThread
Отправлено: Sergeich от Июнь 05, 2006, 17:59
Цитата: "ElderOrb"
Почему нет?.. Единственный нюанс - придётся обвешать эту переменную мьютексами..

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


Название: доступ к переменным и объектам в QThread
Отправлено: QCasper от Июнь 07, 2006, 11:15
Цитата: "Sergeich"
Цитата: "ElderOrb"
Почему нет?.. Единственный нюанс - придётся обвешать эту переменную мьютексами..

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


а если переменная - указатель или объект класса, volatile прокатит?


Название: доступ к переменным и объектам в QThread
Отправлено: alex0303 от Июнь 07, 2006, 11:31
В общем случае для нормального межпоточного взаимодействия необходима атомарность операций.
При этом volatile атомарность не обеспечивает. (А если в ряде случаев и обеспечивает, так это стоит рассматривать как случайность. :)  )

Поэтому ИМХО объекты синхронизации желательно (читай необходимо) использовать всегда, иначе работающий код перестаёт работать при смене платформы, компилятора, кол-ва ядер процев и т.д. А баги эти ох как не легко отлавливать.


Название: доступ к переменным и объектам в QThread
Отправлено: QCasper от Июнь 07, 2006, 13:09
Цитата: "alex0303"
В общем случае для нормального межпоточного взаимодействия необходима атомарность операций.
При этом volatile атомарность не обеспечивает. (А если в ряде случаев и обеспечивает, так это стоит рассматривать как случайность. :)  )

Поэтому ИМХО объекты синхронизации желательно (читай необходимо) использовать всегда, иначе работающий код перестаёт работать при смене платформы, компилятора, кол-ва ядер процев и т.д. А баги эти ох как не легко отлавливать.


что-то я плохо тебя понял, какие объекты синхронизации?
так что мне делать в результате? допутим у меня в классе наследованном от qthread в run происходит что-то типа while(!stoped) {l.append(file.readLine());} где l это QStringList, значит мне надо сделать так:

Код:
run () {
while(!stopped){
mutex.lock();
l.append(file.readLine());
mutex.unlock();
}


а доступ так:

Код:
QStringList getList() {
QMutexLocker ml(&mutex);
return l;
}


???


Название: доступ к переменным и объектам в QThread
Отправлено: alex0303 от Июнь 07, 2006, 15:41
Цитата: "QCasper"

что-то я плохо тебя понял, какие объекты синхронизации?


Да всё те же мютексы, семафоры и т.д. Применительно к Qt QMutex (и QMutexLocker), QSemaphore.

Цитата: "QCasper"

так что мне делать в результате? допутим у меня в классе наследованном от qthread в run происходит что-то типа while(!stoped) {l.append(file.readLine());} где l это QStringList, значит мне надо сделать так:

Код:
run () {
while(!stopped){
mutex.lock();
l.append(file.readLine());
mutex.unlock();
}


а доступ так:

Код:
QStringList getList() {
QMutexLocker ml(&mutex);
return l;
}



Примерно так, но вот не уверен насчёт
Код:
QStringList getList() {
QMutexLocker ml(&mutex);
return l;
}

Во первых деструктор QMutexLocker отработает раньше чем скопируется строка, во вторых QString относится к Shared Classes и реально строка копируется только при её изменении (или принудительно).

добавлено спустя 4 минуты:

 УПС. Там не QString, а QStringList. Но смысл тотже?


Название: доступ к переменным и объектам в QThread
Отправлено: QCasper от Июнь 07, 2006, 18:48
Цитировать
Во первых деструктор QMutexLocker отработает раньше чем скопируется строка, во вторых QString относится к Shared Classes и реально строка копируется только при её изменении (или принудительно).

добавлено спустя 4 минуты:

 УПС. Там не QString, а QStringList. Но смысл тотже?


тогда так:

Цитировать
QStringList getList() {
     QMutexLocker ml(&mutex);
     QStringList l1(l);
     return l1;
}


???

и что значит "примерно"? :)


Название: доступ к переменным и объектам в QThread
Отправлено: Steven_Orko от Июнь 07, 2006, 19:46
Приведи весь класс своего потока и опиши, что он делать будет, потому как то, что здесь тебе уже посоветовали, уведет тебя далекоооо...


Название: доступ к переменным и объектам в QThread
Отправлено: QCasper от Июнь 07, 2006, 22:05
Цитата: "Steven_Orko"
Приведи весь класс своего потока и опиши, что он делать будет, потому как то, что здесь тебе уже посоветовали, уведет тебя далекоооо...


я ж привел, единственный ньюанс, что вместо l.append(file->readLine()) будет некая ф-ция, которая в зависимости от флага считывает строку либо из файла либо еще откуда, из БД например, но в данный момент код точно такой

Код:
void MessageReceiver::run() {
mutex.lock();
if (!enabled) {
mutex.unlock();
return;
}
stopped = false;
mutex.unlock();

openSource();
if (!opened) return;
while (!stopped) {
QString s(getMessage());
mutex.lock();
m_MessageList.append(s);
mutex.unlock();
msleep(1000);
}
closeSource();
}