#multithreading #c 11 #syntax #most-vexing-parse
#многопоточность #c 11 #синтаксис #самый неприятный синтаксический анализ
Вопрос:
#include <iostream>
#include <thread>
class DisplayThread
{
public:
void operator()()
{
for(int i = 0; i < 10000; i )
std::cout<<"Display Thread Executing"<<std::endl;
}
};
int main()
{
//line 1:
std::thread threadObj( (DisplayThread()) );
for(int i = 0; i < 10000; i )
std::cout<<"Display From Main Thread "<<std::endl;
std::cout<<"Waiting For Thread to complete"<<std::endl;
threadObj.join();
std::cout<<"Exiting from Main Thread"<<std::endl;
return 0;
}
В строке 1: если я использую что-то вроде «threadObj(DisplayThread())», это дает
ошибка, указывающая на отсутствие типа класса.
Может кто-нибудь сказать мне, почему функтор при передаче в конструктор потока должен быть внутри фигурных скобок «()»?
Комментарии:
1.
std::thread threadObj(testObj());
вызываетDisplayThread::operator()()
. Я думаю, вы хотите, чтобы поток вызывал его вместо этого.
Ответ №1:
Поздравляю … в некотором роде: вы стали жертвой явления C , известного как самый неприятный синтаксический анализ: в основном, тенденция компилятора интерпретировать ваши утверждения как объявления функций. Вы не виноваты — это результат двусмысленности в языке, который, оказывается, решается несколько неинтуитивным способом.
Ошибка, которую вы получаете, когда вы удаляете круглые скобки вокруг DisplayThread()
, является:
<source>: In function 'int main()':
<source>:20:15: error: request for member 'join' in 'threadObj', which is of
non-class type 'std::thread(DisplayThread (*)())'
20 | threadObj.join();
| ^~~~
Компилятор считает, что threadObj
это функция, которая принимает указатель на функцию и возвращает std::thread
!
Это решается, если вы используете фигурные скобки для построения без аргументов, например:
std::thread threadObj{ DisplayThread{} };
Комментарии:
1. спасибо за ответ. Не знал об этом явлении. Сегодня узнал кое-что новое.
2. @StraightCirle: Конечно, вы не знали об этом, вот почему поначалу это всех раздражает …