当前位置:网站首页>17.11 std:: atomic continuation, std:: async in-depth discussion

17.11 std:: atomic continuation, std:: async in-depth discussion

2022-06-26 01:46:00 zzyzxb

One : Atomic manipulation std::atomic Continued discussion

commonly atomic Atomic manipulation , in the light of ++、–、+=、&=、|=、*= Is to support the .

std::atomic<int> g_mycout = 0;  // This is an atomic integer type variable , Can be used as an integer variable 
void mythread()
{
	for (int i = 0; i < 1000000; i++)
	{
		//g_mycout++;  // The corresponding operation is atomic operation , Will not be interrupted .
		//g_mycout += 1;  // Support 
		g_mycout = g_mycout + 1;  // The result is not right 
	}
	return;
}

int main()
{
	thread myobj1(mythread);
	thread myobj2(mythread);
	myobj1.join();
	myobj2.join();
	cout << " Both threads have finished executing , The final g_mycout The result is : " << g_mycout << endl;
	cout << "main End of main function execution " << endl;  // Finally, execute this sentence , The whole process exits 
	return 0;
}

Two :std::async In depth talk

<1>std::async Parameter details ,async Used to create an asynchronous task

int mythread1() {
	std::chrono::milliseconds dura(5000);
	std::this_thread::sleep_for(dura);
	cout << "mythread start " << "threadId = " << std::this_thread::get_id() << endl;
	return 1;
}

int main()
{
	cout << "main start " << "threadId = " << std::this_thread::get_id() << endl;
	std::future<int> result = std::async(mythread1);
	cout << result.get() << endl;
	cout << "main End of main function execution " << endl;  // Finally, execute this sentence , The whole process exits 
	return 0;
}

Delay call parameters std::launch::deferred, as well as std::launch::async Force the creation of a thread .
std::thread() If the system resources are tight , Then the thread creation may fail , perform std::thread() The whole program may crash .
std::async() It is not generally called thread creation ( explain async Ability to create threads ), It is generally called to create an asynchronous task .
std::thread() and std::async() The most obvious difference , Namely async Sometimes new threads are not created .

(1) If you use std::launch::deferred To call async What will happen? ?
deferred Delay call , And do not create new threads , Delay to future Object call .get() perhaps wait() Only when mythread(), If not called get perhaps wait, They don't execute .

(2) std::launch::async: Force this asynchronous task to execute on a new thread , This means that the system must create a new thread to run mythread().

(3) std::launch::async | std::launch::deferred
Here it is. | signify async The behavior of may be to create a new thread and execute it immediately, or not to create a new thread and delay until the call result.get() Before starting to execute the task entry function .

(4) Without additional parameters , Bring async Function an entry function name ; Actually , The default value should be std::launch:async | std::launch::deferred, and (3) The effect is exactly the same .
let me put it another way : The system will decide to be asynchronous ( Create a new thread ) Or synchronization? ( Don't create a new thread ) Way to run .

int mythread1() {
	std::chrono::milliseconds dura(5000);
	std::this_thread::sleep_for(dura);
	cout << "mythread start " << "threadId = " << std::this_thread::get_id() << endl;
	return 1;
}

int main()
{
	cout << "main start " << "threadId = " << std::this_thread::get_id() << endl;
	std::future<int> result1 = std::async(mythread1);
	std::future<int> result2 = std::async(std::launch::deferred, mythread1);
	std::future<int> result3 = std::async(std::launch::deferred | launch::async, mythread1);
	cout << result1.get() << endl;
	cout << "main End of main function execution " << endl;  // Finally, execute this sentence , The whole process exits 
	return 0;
}

What does it mean to decide for yourself ? How the system decides to be asynchronous ( Create a new thread ) Or synchronization? ( Don't create a new thread ) Way to run .

<2>std::async and std::thread The difference between

std::thread Create thread , If the system resources are tight , Failed to create thread , Then the whole program will report an abnormal crash .

int mythread() { return 1;}
std::thread mytobj(mythread);
mytobj.join();
std::thread How to create threads , If the thread has a return value , It is not easy to get this value .

std::async Create asynchronous tasks , Threads may or may not be created , also async It is easy to get the return value of the thread entry function by calling the method .
Due to system resource constraints :
(1) If std::thread Too many threads created , The creation may fail , The system reported an exception , Run away .

(2) If std::async, Generally, it will not run away , If the system resources are tight and it is impossible to create a new thread ,std::async This call without additional parameters does not create a new thread . It's who calls result.get() To ask for results , So this asynchronous task mythread It runs in the execution of this result.get() On the thread where the statement is located .

(3) The number of threads in a program should not exceed 100-200, Time slice .

<3>std::async Solution of uncertain problems

Without additional parameters std::async call , Let the system decide whether to create a new thread .
The focus of the problem is std::future result = std::async(mythread); How to write it .
Whether the asynchronous task has been delayed or not ,(std::launch::async still std::launch::deferred)?

std::future Object's wait_for function

int mythread1()
{
	std::chrono::milliseconds dura(5000);
	std::this_thread::sleep_for(dura);
	cout << "mythread start " << "threadId = " << std::this_thread::get_id() << endl;
	return 1;
}

int main()
{
	cout << "main start " << "threadId = " << std::this_thread::get_id() << endl;
	std::future<int> result = std::async(mythread1);
	//std::future_status status = result.wait_for(std::chrono::seconds(0));
	std::future_status status = result.wait_for(6s);
	if (status == std::future_status::deferred)
	{
		// The thread is delayed ( System resources are tight , System USES std::launch::deferred Strategy )
		cout << result.get() << endl;  // Only then will it be called mythread()
	}
	else
	{
		// The mission has not been delayed , It's already running , The thread is created ;
		if (status == std::future_status::ready) {
			// The thread successfully returned 
			cout << " The thread executes successfully and returns !" << endl;
			cout << result.get() << endl;
		}
		else if (status == std::future_status::timeout) {
			// The timeout thread has not finished executing 
			cout << " The timeout thread did not finish executing !" << endl;
			cout << result.get() << endl;
		}
	}
	cout << "main End of main function execution " << endl;  // Finally, execute this sentence , The whole process exits 
	return 0;
}
原网站

版权声明
本文为[zzyzxb]所创,转载请带上原文链接,感谢
https://yzsam.com/2022/177/202206260001542027.html