如何在线程之间同步数据

时间:2020-07-24 05:22:14

标签: c++ multithreading c++14

这是我的班上打印数据

class PrintData
{
    int data[20];

public:
    void setData(int dataValue[])
    {
        for( int i = 0 ; i < 20; i++)
        data[i] = dataValue[i];
    }
    void Print()
    {
        for (int i = 0; i < 20; i++)
            std::cout << data[i];

        std::cout << std::endl;
    }
};

这是主要功能

int number[20] ;
void updateNumber()
{
    for (int i = 0; i < 1000; i++) {
    //  std::this_thread::sleep_for(std::chrono::milliseconds(1000));
        for (int k = 0; k < 20; k++)
            number[k] = k;
    
        // after one iteration it should wait and after the print.Print() is executed than it should again update the data
    }
}

int main()
{
    PrintData print;
    std::thread t(&updateNumber);
    while (true)
    {
        // if upDateNumber has updated all the numbers than only than only set the number
        print.setData(number);
        
        print.Print();

    }
    return 0;
}

线程中的迭代完成后,应等待print.setData(number)函数执行,该函数执行后,应再次更新数据。

如果调用了print.setData(number)并且线程仍未完成对数组的更新,那么print.setData(number)不应更新数据。

2 个答案:

答案 0 :(得分:1)

希望对您有所帮助:(信号量是Qt的QSemaphore的自我实现)

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


class semaphore
{
public:
    semaphore(int n = 0) : m_n(n) 
    {
    }

public:
    void acquire(int n = 1)
    {
        std::unique_lock <std::mutex> lk(m_buf_mut);

        while (m_n < n) {
            m_cv.wait(lk);
        }

        m_n -= n;

    }

    void release(int n = 1)
    {
        {
            std::unique_lock <std::mutex> lk(m_buf_mut);
            m_n += n;
        }

        m_cv.notify_all();
    }

    bool tryAcquire(int n = 1)
    {
        std::unique_lock <std::mutex> lk(m_buf_mut);

        if (m_n >= n) {
            m_n -= n;
            return true;
        }

        return false;
    }


private:
    std::mutex m_buf_mut;
    int m_n;
    std::condition_variable m_cv;
};

class PrintData
{
    int data[20];

public:
    void setData(int dataValue[])
    {
        for( int i = 0 ; i < 20; i++)
        data[i] = dataValue[i];
    }
    void Print()
    {
        for (int i = 0; i < 20; i++)
            std::cout << data[i];

        std::cout << std::endl;
    }
};


int number[20] ;
void updateNumber(semaphore *freeSem, semaphore *usedSem)
{
    for (int i = 0; i < 1000; i++) {
    //  std::this_thread::sleep_for(std::chrono::milliseconds(1000));
    //
    
        freeSem->acquire();

        for (int k = 0; k < 20; k++)
            number[k] = k;

        usedSem->release();
    
        // after one iteration it should wait and after the print.Print() is executed than it should again update the data
    }
}

int main()
{
    PrintData print;

    semaphore freeSem(1);
    semaphore usedSem(0);

    std::thread t(&updateNumber, &freeSem, &usedSem);
    while (true)
    {
        // if upDateNumber has updated all the numbers than only than only set the number
        usedSem.acquire();
        print.setData(number);
        
        print.Print();
        freeSem.release();

    }
    return 0;
}

答案 1 :(得分:1)

一个涉及producer consumer的{​​{1}}问题的简单示例就是这样:

conditional variables

您可以使用不同的逻辑和实现方式。