В чем причина ошибки std@bad_function_call при создании потока
Есть следующий код:
std::function<void()> f=[](){std::cout<<"Yaha";};
std::thread thr1(f);
std::thread thr2(f); //Здесь возникает ошибка std@bad_function_call
Прошу подсказать причину возникновения данной ошибки. Как я понимаю объект f становится пустым (не пойму почему).
И второй вопрос:
void thr1_f()
{
std::cout<<"Yaha";
}
в чем разница в std::thread(thr1_f) и std::thread(&thr1_f) и когда какой вариант следует использовать? Почему нельзя вызвать std::thread(&f) (а нужно использовать std::thread(std::ref(f))?
Заранее благодарю!
Ответы (1 шт):
std@bad_function_call можно получить, если внутри фукнции лежит nullptr.
Смотрим снова в документацию и видим такое
template< class Function, class... Args >
explicit thread( Function&& f, Args&&... args );
ага, нужно, что бы move конструктор отработал и можно получить такой эффект. Так как автор вопроса упоминает о передаче по ссылке и по std::ref, сделаем маленький шаг в сторону
std::function<void()> f=[](){std::cout<<"Yaha";};
std::thread thr1(std::move(f));
std::thread thr2(f);
thr1.join();
thr2.join();
и получим желаемую ошибочку. std::move провоцирует вызов move конструктора, который в случае std::function зануляет указатель.
А возможно, компилятор у Embarcadero RAD Studio такой хитрый, что вызывает move конструктор. или там сам std::thread объявлен с std::forward, надо смотреть в сам код. я этого проверить не могу.