2017-01-08 3 views
2

Я путаю скорость, отличающуюся от использования блокировки мьютекса() и разблокировки() внутри и снаружи цикла for. Я получил значение глобальной переменной и функцию, которая увеличивает его 1000000 раз. Эта функция запускается параллельно 5 потоками. Я измерил время, прошедшее и получил следующие результаты:Разница скорости блокировки Mutex внутри и снаружи петли фока

mutex.lock(); 
    for(int i = 0; i < 1000000; i++) 
    { 
     value++; 
    } 
    mutex.unlock(); 

0.160921 секунды

и:

for(int i = 0; i < 1000000; i++) 
    {   
     mutex.lock(); 
     value++; 
     mutex.unlock(); 
    } 

2.10521 секунды

Я полагаю, со вторым внутренним устройством мьютекса управления слишком отлично, и много времени проводится между переключением потоков? или есть что-то еще?

ответ

3

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

И в первом случае компилятор мог бы просто заменить цикл на одно дополнение. И поскольку вся функция потока покрыта мьютексом, нет параллельного выполнения; все потоки, кроме одного, блокируются только до тех пор, пока цикл одного не будет завершен, а это означает, что код эквивалентен простому циклу пять раз подряд в одном потоке.

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

Вместо этого речь идет о том, нужно ли блокировать мьютекс только на короткое время, оставляя при этом остальное время, чтобы другие потоки работали или блокировали его на более длительные периоды, чтобы избежать накладных расходов, но уменьшая параллелизм. Однако, поскольку ваши потоки не делают ничего, кроме доступа к защищенному ресурсу, нет «остальной части времени». Ваша проблема (приращение целого числа 5000000 раз) не имеет врожденного параллелизма в первую очередь и, следовательно, ничто для использования нескольких потоков.

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