2016-02-27 2 views
1

Я узнаю о мьютексах, и я вижу, что для использования защиты блокировки на каждой итерации вам нужно выделить память для защиты блокировки, вызвать конструктор, а затем вызвать деструктор. Похоже, что это может быть значительным объемом накладных расходов по сравнению с блокировкой, которая никогда не выходит за рамки. Я понимаю преимущество блокировки, но сколько времени я могу сэкономить, избегая их? Или, другими словами, насколько мала работа потока на итерацию, чтобы сделать надстройку блокировки значимой?boost :: lock_guard распределение, конструктор и служебные данные деструктора

prepare_data(); 
{ 
    boost::lock_guard<boost::mutex> lock(mut); 
    data_ready=true; 
} 
cond.notify_one(); 

ответ

3

Не требуется распределение. Компилятор может точно определить, что делает конструктор и деструктор, и оптимизировать необходимость в любом распределении памяти или инициализации объекта или любой необходимости вызывать конкретную конструктор или функцию деструктора.

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

Это одна из основных причин, по которой RAII рекомендуется на C++ - обычно это не требует затрат.

0

Компилятор, скорее всего, должен будет выделить пространство в стеке, чтобы сохранить ссылку на мьютекс для деструктора lock_guard. Это вряд ли будет кэшировать его, потому что (а) блокировка/разблокировка мьютекса являются внешними вызовами функций и (б) функции накладывают забор памяти. Но стоимость блокировки/разблокировки мьютекса намного больше, чем другие операции, связанные с lock_guard, что нет практических причин, чтобы избежать этого. Кроме того, современные компиляторы имеют очень эффективные методы управления стеками, и выделение пространства для ссылки может фактически быть не-операцией.

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