condition_variable::wait in C++

Hello everyone, in this tutorial, we will learn about the condition variable in C++. Before starting this condition variable you should have prior knowledge of multithreading (if not please refer this Multithreading in C++).

What is the condition variable?
A condition variable is an object which enables the thread to wait until it is notified to resume. Whenever condition variable is used a mutex is required. The following are the main member functions of a condition variable.

  1. wait(): This function is used to block the current thread until a condition variable is woken up.
  2. notify_one(): This function is used to notify only one waiting thread.
  3. notify_all(): This function is used to notify all the waiting threads.

C++: condition_variable::wait

We will learn about condition_variable::wait using the following code

#include <iostream>
#include <thread>
#include <mutex>
#include <condition_variable>

std::condition_variable cv;
std::mutex m;
int balance = 0;

void deposite(int money)
{
    std::unique_lock<std::mutex> ul(m);  //lock is applied on mutex m by thread t2
    balance += money;
    std::cout<<money<<" Rs deposited to the account \n";
    cv.notify_one();  //notify to condition variable
}

void withdraw(int money)
{
     std::unique_lock<std::mutex> ul(m);  //lock is applied on mutex m by thread t1
     cv.wait(ul,[] {return (balance!=0) ? true : false;});  //waits until the condition becomes true
     if(balance>=money)
       {
         balance -= money;
         std::cout<<money<<" Rs deducted from the account \n";
       }
     else std::cout<<"Low balance \n";
     std::cout<<"Total balance is:" <<balance;       
}

int main()
{
  std::thread t1(withdraw,1000);  //create thread t1
  std::thread t2(deposite,1000);  //create thread t2
  
  t1.join();
  t2.join();
  
  return 0;
}

Output:

1000 Rs deposited to the account
1000 Rs deducted from the account
Total balance is:0

As it is multithreading, both the threads will be running concurrently and there can be two cases. Either the thread t1 starts first i.e. withdraw function or the thread t2 starts first i.e. deposit function.

CASE 1: Thread t1 starts first i.e. the withdraw function.

  • In this case thread t1 starts first and the lock is applied on mutex m by thread t1 so the thread t2 goes in the wait state.
  • Thread t1 calls wait() on condition variable cv and then checks the condition. In this case, the balance is zero. Thus it returns false and the lock is released and waits for a condition variable to get signalled.
  • So now thread t2 applies lock on mutex m. Now the money is deposited in the account and then it will notify the condition variable using notify_one() function. This function is used because only one thread is in the waiting state.
  • Now the thread t1 which was in wait state resumes, the condition is checked again. The money is deposited so the balance is not equal to zero and it returns a true value. Therefore the money will be deducted from the account.

CASE 2:Thread t2 starts first i.e. deposit function.

  • In this case thread t2 starts first and the lock is applied on mutex m by thread t2, so the thread t1 goes in the wait state.
  • Now the money is being deposited to the account and then it will notify the condition variable using notify_one() function.
  • Now thread t1 applies lock and calls wait() function on condition variable cv and then checks the condition. So in this case, the money is already deposited. Therefore balance is not equal to zero and returns true so now the money is deducted from the account.

NOTE: In both cases the output will be the same.

Also read,

Leave a Reply

Your email address will not be published. Required fields are marked *