2014-11-11 2 views
0

Я использую mutlithreading 'first time' для сетевого приложения, мой вопрос - две связанные части, Если я представляю, например, кучу сообщений в udp с классами (каждое сообщение класса), было бы хорошей практикой делать экземпляры таких классов глобальными, чтобы отправлять их в разных потоках, или лучший подход заключается в использовании структуры, содержащей экземпляр класса, и всю информацию о сокетах в качестве ссылки внутри этой структуры (затем используйте Pthread_create)Многопоточные и глобальные экземпляры классов?

Я считаю что в первом варианте необходимо соблюдать большую осторожность, чтобы избежать одновременного доступа к данным (используйте pthread_mutex)

, пожалуйста, предложите, как бы вы приблизились к этой проблеме.

Я действительно был бы признателен thehelp

Большое спасибо

+0

Вам не нужно использовать потоки для сетевого программирования. Используйте 'select()' или эквивалент вашей платформы. Или 'libev'. –

+0

Если вы идете на C++ 11 или c11, и ваш компилятор поддерживает потоки, вы должны использовать это вместо pthreads. – didierc

+0

Избегайте ситуаций, когда многие потоки должны делиться одним значением (и таким образом синхронизировать его использование). – didierc

ответ

0

Если я правильно понимаю ваш вопрос, вы планируете иметь слушающий поток, receveives сообщения и отправляет их в несколько потоков, которые обрабатывают эти сообщения concurently.

Здесь возможный подход будет использовать совместно queue:

  • Читающих мысли push() сообщения, которые он получает по очереди:
  • рабочих потоков, если очередь не empty(), возьмите следующий элемент для обработки (front()``and pop() `)
  • Конечно, очередь должна быть заблокирована при чтении или записи элементов с помощью mutex, если только вы не используете реализацию очереди без lokc.

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

С 11 standard threads C++ это будет выглядеть примерно так:

... 
    std::queue<my_message_class> work_to_do;  // create queue 
    std::thread t1(listener, std::ref(work_to_do)); // launch listener 
    int n = max(2, std::thread::hardware_concurrency()-1); // maximize concurency for the hardware 
    std::vector<std::thread> workers; 
    for (int i = 0; i < n; i++) { 
     v.push_back(std::thread{ worker_function, std::ref(work_to_do) }); 
    } 
    ... // do something else and wait until it finishes 
    t1.join(); // wait until listner finishes 
    for (auto& x : workers) { // wait until all the worker threads finish. 
     x.join(); 
    } 
    ... 

где void listener(std::queue<my_message_class>& q) и void worker(std::queue<my_message_class>& q) бы функции для выполнения.

Конечно, вы можете делать похожие вещи с помощью pthreads. Но стандарты имеют то преимущество, что они независимы от платформы.

Смежные вопросы