Ниже приведен пример из C ++ параллелизма в действии $ 2.2
void f(int i,std::string const& s);
void oops(int some_param)
{
char buffer[1024];
sprintf(buffer, "%i",some_param);
std::thread t(f,3,buffer);
t.detach();
}
И автор говорит, что это неопределенное поведение:
В этом случаеэто указатель на локальную переменную buffer
, которая передается в новый поток, и существует значительная вероятность того, что функция упс выйдет до того, как буфер будет преобразован в std::string
в новом потоке, что приведет к неопределенное поведение .Решение заключается в приведении к std::string
перед передачей буфера в конструктор std :: thread:
void f(int i,std::string const& s);
void not_oops(int some_param)
{
char buffer[1024];
sprintf(buffer,"%i",some_param);
std::thread t(f,3,std::string(buffer));
t.detach();
}
Но я запутался в этом.Потому что, насколько я понимаю, нет никакой разницы между двумя формами:
В первом фрагменте кода при передаче buffer
функции в качестве параметра также будет создан временный объект std::string
и связать параметр функции с этим временным объектом. Так что это точно так же со вторым фрагментом кода. Единственное отличие состоит в том, что временный объект в первом объекте генерируется неявно компилятором, а второй явно пользователем.