Многопоточность с использованием пула потоков - PullRequest
2 голосов
/ 13 мая 2011

В настоящее время я использую пул потоков Boost с количеством потоков, равным количеству ядер. Я запланировал, скажем, 10 задач, используя функцию расписания пула. Например, предположим, у меня есть функция

void my_fun(std::vector<double>* my_vec){
    // Do something here
}

Аргумент 'my_vec' здесь просто используется для выполнения некоторых временных вычислений. Основная причина, по которой я передал ей функцию, заключается в том, что я хотел бы повторно использовать этот вектор при повторном вызове функции.

В настоящее время у меня есть следующее

// Create a vector of 10 vectors called my_vecs

// Create threadpool
boost::threadpool::pool tp(num_threads);

// Schedule tasks
for (int m = 0; m < 10; m++){
    tp.schedule(boost::bind(my_fun, my_vecs.at(m)));
}

Это моя проблема: я хотел бы заменить вектор из 10 векторов только на 2 вектора. Если я хочу запланировать 10 задач и у меня есть 2 ядра, в любое время будет работать максимум 2 потока (задачи). Поэтому я хочу использовать только два вектора (по одному назначен каждому потоку) и использовать его для выполнения моих 10 задач. Как я могу это сделать?

Надеюсь, это понятно. Спасибо!

Ответы [ 4 ]

1 голос
/ 13 мая 2011

Я бы не стал ограничивать количество потоков количеством ядер.Помните, что многопоточное программирование происходило задолго до того, как у нас были многоядерные процессоры.Это связано с тем, что потоки, скорее всего, заблокируют какой-либо ресурс, а следующий поток может подключиться и использовать процессор.

1 голос
/ 13 мая 2011

Вероятно boost::thread_specific_ptr - это то, что вам нужно.Ниже описано, как вы можете использовать его в своей функции:

#include <boost/thread/tss.hpp>
boost::thread_specific_ptr<std::vector<double> > tls_vec;

void my_fun()
{
    std::vector<double>* my_vec = tls_vec.get();
    if( !my_vec ) {
        my_vec = new std::vector<double>();
        tls_vec.reset(my_vec);
    }
    // Do something here with my_vec
} 

Он будет повторно использовать векторные экземпляры между задачами, запланированными для одного и того же потока.Может быть более 2 экземпляров, если в пуле больше потоков, но из-за вытеснения, упомянутого в других ответах, вам действительно нужен экземпляр для каждого выполняемого потока, а не для ядра.

Вам не нужно удалять векторэкземпляры хранятся в thread_specific_ptr;они будут автоматически уничтожены по окончании соответствующих потоков.

0 голосов
/ 13 мая 2011

Несмотря на то, что это два, только два потока могут быть запланированы одновременно, во многих системах потоков потоки разделены по времени, поэтому поток получает преимущество при выполнении своей задачи.Следовательно, третий (четвертый, ...) поток получит возможность работать, в то время как обработка первого и второго еще не завершена.

Я не знаю об этой конкретной реализации потоков, но я предполагаю, чточто это позволит (или работать в средах, поддерживающих) упреждающее планирование.Мой способ думать о потоках - стараться сделать его по-настоящему простым, пусть каждый поток имеет свои собственные ресурсы.

0 голосов
/ 13 мая 2011

У Java есть FixedThreadPool.

похоже, что Boost может иметь что-то похожее

http://deltavsoft.com/w/RcfUserGuide/1.2/rcf_user_guide/Multithreading.html

По сути, фиксированный пул потоков порождает фиксированное количество потоков, а затемВы можете ставить задачи в очередь менеджера.

...