你的位置:首页 > 信息动态 > 新闻中心
信息动态
联系我们

操作系统 读写问题(读者优先写者优先)

2021/12/31 18:43:09

操作系统要期末考了,读写问题之前一直弄不清楚,现在结合伪代码谈一下个人理解

读者优先

要求

读者优先问题:

  1. 允许多个读者读取;
  2. 读者在读的时候不能有写者在写;
  3. 不允许多个写者同时写;
  4. 如果写者申请写的时候有多个读者申请读,那么先读后写

分析

读者优先中,可以由多个写者和多个读者,那么需要用readercount和writercount记录

某时刻下存在的读者和写者数量,一旦存在读者/写者,立刻封锁startwr,直到所有count为0时再释放

需要使用以下信号量:

startwr:开启读/写进程

NowRW:现在是读者/写者的时间,可以控制Reader和Writer的顺序

Rmutex:使得多个读者依次进行

Wmutex:使得多个写者依次进行

伪代码

int Rmutex=0,Wmutex=0;
int RW=0,readercount=0,writercount=0;
int startrw=0;

void Reader(){
    // 防止同时涌入多个Reader
    wait(Rmutex);
    readercount++;
    if(readercount==1){
        // 关键点
        wait(RW);
    }
    signal(Rmutex);

    // ---------------------
    wait(startrw);
    //start reading...
    siganl(startrw);
    // ---------------------

    wait(Rmutex);
    readercount--;
    if(readercount==0){
        signal(RW);
    }
    signal(Rmutex);

}

void Writer(){
    // 防止同时涌入多个Writer
    wait(Wmutex);
    wait(RW);
    writercount++;
    if(writercount==1){
        // 关键点
        wait(startrw);
    }
    signal(RW);
    signal(Wmutex);
    
    // ---------------------
    //start writing...
    // ---------------------
	
    wait(Wmutex);
    writercount--;
    if(writercount==0){
        signal(startrw);
    }
    signal(Wmutex);
}

关键点

为什么if(writercount1)限制的是startwr,if(readercount1)限制的是NowRW?

原因是startwr只是限制读写操作的执行,NowRW可以控制reader和writer的添加。

我们设置一组测试用例:reader、writer、reader、reader、writer

按照代码,

1.首先reader进入,封锁NowRW,注意readercount变为1,所以后面的两个writer无法添加,直接添加后面两个reader;

2.三个reader依次进行读操作

3.两个writer依次进行写操作。读者优先效果达成;

写者优先

要求

写者优先问题:

1.允许多个读者读取;

2.读者在读的时候不能有写者在写;

3.不允许多个写者同时写;

4.如果读者申请读的时候已经有写者在写或申请写,那么所有写者写完之后读者才能读

分析

其实和读者优先问题差不多,需要用readercount和writercount记录某时刻下存在的读者和写者数量,一旦存在读者/写者,立刻封锁startwr,直到所有count为0时再释放

需要使用以下信号量:

startwr:开启读/写进程

NowRW:现在是读者/写者的时间,可以控制Reader和Writer的顺序

Rmutex:使得多个读者依次进行

Wmutex:使得多个写者依次进行

伪代码(和读者优先类似,只是更换关键点的位置)

int startwr = 0, NowRW = 0, Rmutex = 0, Wmutex = 0;
int readercount = 0, writercount = 0;

void Reader()
{
    // 防止同时涌入多个Reader
    wait(Rmutex);
    // 进入读状态
    wait(NowRW);
    //prepare for reading...
    readercount++;
    if (readercount == 1)
    {
        wait(startwr);
    }
    signal(NowRW);
    signal(Rmutex);

     // -----------------------
    // start reading...
    readthings();
     // -----------------------

    wait(Rmutex);
    readercount--;
    if (readercount == 0)
    {
        // 说明所有Reader已经读完,可以开始写了
        signal(startwr);
    }
    signal(Rmutex);
}

void Writer()
{
    // 防止同时涌入多个Writer
    wait(Wmutex);
    writercount++;
    if (writercount == 1)
    {
        wait(NowRW);
    }
    signal(NowRW);
    signal(Wmutex);

    // -----------------------
    wait(startwr);
    // start writing
    writethings();
    signal(startwr);
    // -----------------------

    wait(Wmutex);
    writercount--;
    if (writercount == 0)
    {
        signal(NowRW);
    }
    signal(Wmutex);
}

关键点

还是刚才那组测试用例:reader、writer、reader、reader、writer

按照代码,

1.首先reader进入,封锁NowRW,然后开始读,读之后释放NowRW;

2.然后writer进入,注意writercount变为1,所以后面的两个reader无法添加,直接添加最后一个writer

3.两个writer依次进行写操作;

4.最后的两个reader一次进行读操作