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

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

Страниц: 1 2 [3]   Вниз
  Печать  
Автор Тема: Вопрос ламера о реализации многопоточности  (Прочитано 22276 раз)
Hvzh
Гость
« Ответ #30 : Декабрь 14, 2016, 13:44 »

Думаю, скорее второе... Буду проверять. Сейчас у меня вот так. После старта потоков  начинается ожидание ответа от потока, оформленное в виде бесконечного цикла:

Код:
    for(;;)
    {
        if(сameraID == 0)
            continue;
        else
        {
            std::cout << "StartController::service new camera ID = " << cameraID << std::endl ;
            break;
        }
    }

Значение cameraID должно менятся в слоте, который выглядит вот так:
Код:
void StartController::cameraStarted(int id)
{
    cameraID = id;
    qDebug() << "StartController::cameraStarted: cameraID = " << cameraID;
}
Может, вся проблема из-за цикла?
Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #31 : Декабрь 14, 2016, 13:55 »

Блин, конечно из-за цикла. Зачем тебе цикл нужен?
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Hvzh
Гость
« Ответ #32 : Декабрь 14, 2016, 14:01 »

Вот полная функция:

Код:
void StartController::service(HttpRequest &request, HttpResponse &response) {
    QJsonObject json;

    cameraID = 0;
    newCameraID = 0;

    QByteArray url = request.getParameter("url");
    QByteArray minArea = request.getParameter("minArea");
    QByteArray maxArea = request.getParameter("maxArea");
    QByteArray startx = request.getParameter("x0");
    QByteArray starty = request.getParameter("y0");
    QByteArray endx = request.getParameter("x1");
    QByteArray endy = request.getParameter("y1");

    dbthread = new QThread;
    impthread = new QThread;

    worker = new DbWriteWorker();
    worker->setInterval(60);
    worker->moveToThread(dbthread);

    impworker = new ImageProcessingWorker(0, QString::fromUtf8(startx).toInt(), QString::fromUtf8(starty).toInt(),
                                          QString::fromUtf8(endx).toInt(), QString::fromUtf8(endy).toInt(),
                                          QString::fromUtf8(minArea).toInt(), QString::fromUtf8(maxArea).toInt(), 1, QString::fromUtf8(url));
    impworker->moveToThread(impthread);
    // Соединяем сигнал started потока, со слотом process "рабочего" класса, т.е. начинается выполнение нужной работы.
    connect(dbthread, SIGNAL(started()), worker, SLOT(process()));
    connect(impthread, SIGNAL(started()), impworker, SLOT(process()));

    // По завершению выходим из потока, и удаляем рабочий класс
    connect(worker, SIGNAL(finished()), dbthread, SLOT(quit()));
    connect(worker, SIGNAL(finished()), worker, SLOT(deleteLater()));
    connect(impworker, SIGNAL(finished()), impthread, SLOT(quit()));
    connect(impworker, SIGNAL(finished()), impworker, SLOT(deleteLater()));

    // Удаляем поток, после выполнения операции
    connect(dbthread, SIGNAL(finished()), dbthread, SLOT(deleteLater()));
    connect(impthread, SIGNAL(finished()), impthread, SLOT(deleteLater()));
    connect(impworker, SIGNAL(sendCounters(int,int, int)), worker, SLOT(waitForDB(int,int,int)));

    //connect(worker, SIGNAL(getDataSignal()), impworker, SLOT(prepareCounters()));

    dbthread->start();
    impthread->start();

    std::cout << "Waiting for new camera connection" << std::endl ;

    for(;;)
    {
        if(сameraID == 0)
            continue;
        else
        {
            std::cout << "StartController::service new camera ID = " << cameraID << std::endl ;
            break;
        }
    }

    if(cameraID > 0)
    {
        json["result"] = "Ok";
    }
    else
    {
         json["result"] = "Error";
    }
    json["cameraID"] = cameraID;

    QJsonDocument saveDoc(json);
    response.write(saveDoc.toJson(),true);
}
« Последнее редактирование: Декабрь 14, 2016, 14:06 от Hermann » Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #33 : Декабрь 14, 2016, 14:06 »

Код
C++ (Qt)
connect(impworker, SIGNAL(newCameraOpened(int)), this, SLOT(cameraStarted(int)));
 
QEventLoop eventLoop;
connect(impworker, SIGNAL(newCameraOpened(int)), &eventLoop, SLOT(quit()));
eventLoop.exec();
 
//Here we know cameraId
 
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #34 : Декабрь 14, 2016, 14:08 »

Если у тебя Qt5 и 11 стандарт, лучше лямбду вместо слота заюзать.

Код
C++ (Qt)
connect(impworker, SIGNAL(newCameraOpened(int)), [&eventLoop, &cameraId] (int id) {cameraId = id; eventLoop.quit();});
 
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Hvzh
Гость
« Ответ #35 : Декабрь 14, 2016, 14:14 »

Сейчас попробую...
Записан
Hvzh
Гость
« Ответ #36 : Декабрь 14, 2016, 14:26 »

Ура, работает. Еще одно огромное спасибо!
Записан
Hvzh
Гость
« Ответ #37 : Декабрь 14, 2016, 14:38 »

Ну, и до кучи еще один вопрос. Есть функция отключения камеры, которая принимает оь браузера один параметр - ID камеры. Сейчас она выглядит так:

Код:
void StopController::service(HttpRequest &request, HttpResponse &response) {
    QJsonObject json;

    camSatus = -1;

    QByteArray par = request.getParameter("id");

    qDebug() << "StopController::ID int = " << par.toInt();

    procToKill = par.toInt();

    for(;;)
    {
        if(procToKill == 0)
            break;
    }

     json["result"] = "Ok";
     json["value"] = par.toInt();

        QJsonDocument saveDoc(json);
    response.write(saveDoc.toJson(),true);
}

Остановка сейчас сделана через глобальную переменную procToKill. Это работает, но вариант совершенно неподходящий при большом количестве подключений. При этом функция о процессах ничего, кроме переданного ID не знает. Я могу послать сигнал, например, stopCamera(cameraID), но как мне ответ поймать? И как заставить impworker этот сигнал ловить?
« Последнее редактирование: Декабрь 14, 2016, 14:45 от Hermann » Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #38 : Декабрь 14, 2016, 14:50 »

У тебя каждая камера это отдельный процесс? Храни мапу соответствия номера камеры и номера процесса. Или я тчо-то не так понял.
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Hvzh
Гость
« Ответ #39 : Декабрь 14, 2016, 14:59 »

Каждая камера - отдельный поток
Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #40 : Декабрь 14, 2016, 15:01 »

Храни где-нибудь мапу соответствия.
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Hvzh
Гость
« Ответ #41 : Декабрь 14, 2016, 15:11 »

Храни где-нибудь мапу соответствия.
Ну, могу я получить ИД потока, но он же, вроде, для внутреннего пользования, и остановить поток используя Thread ID вроде нельзя
Записан
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #42 : Декабрь 14, 2016, 15:22 »

QMap<int, QThread*> threads;
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Пантер
Administrator
Джедай : наставник для всех
*****
Offline Offline

Сообщений: 5876


Жаждущий знаний


Просмотр профиля WWW
« Ответ #43 : Декабрь 14, 2016, 15:23 »

А еще лучше:

QMap<int, YouClass*> m;
m->stop();
Записан

1. Qt - Qt Development Frameworks; QT - QuickTime
2. Не используйте в исходниках символы кириллицы!!!
3. Пользуйтесь тегом code при оформлении сообщений.
Hvzh
Гость
« Ответ #44 : Декабрь 14, 2016, 18:21 »

А еще лучше:

QMap<int, YouClass*> m;
m->stop();
Сделал так. Работает. Еще раз огромное спасибо!
Записан
Страниц: 1 2 [3]   Вверх
  Печать  
 
Перейти в:  


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