product-consumer

 

  1 参考多线程读写文件
  2 以下转贴
  3 using   System;   
  4   using   System.Threading;   
  5   using   System.IO;   
  6     
  7   namespace   CopyTest   
  8   {   
  9     
 10   //FileBuffer用来存放和取出缓冲区变量   
 11   public   class   FileBuffer{   
 12   private   int   m_readsize   =   1024;   
 13   //定义了m_capacity个字节的缓冲区   
 14   private   byte[]   m_buffer   =   new   byte[4096];   
 15   //确认缓冲区内已放字节的个数   
 16   private   int   bufferCount=0;   
 17   //确定读写的位置   
 18   private   int   readLocation=0,writeLocation=0;   
 19     
 20   public   FileBuffer()   {   
 21     
 22   }   
 23     
 24   //从缓冲区中取数据   
 25   public   byte[]   getBuffer()   {   
 26   //加上了共享锁   
 27   lock(this)   {   
 28   //判断如果缓冲区内无内容,则读取者进入wait状态,并且释放对象锁   
 29   if(bufferCount==0)   {   
 30   Console.WriteLine("缓冲区无数据,无法读取");   
 31   Monitor.Wait(this);   
 32   }   
 33     
 34   byte[]   newBuf   =   new   byte[m_readsize];   
 35   Buffer.BlockCopy(m_buffer,   readLocation,   newBuf,   0,   m_readsize);   
 36     
 37   //已经从缓冲区读取了内容,所以bufferCount要进行自减.   
 38   bufferCount-=m_readsize;   
 39   //求余的目的是为了循环使用缓冲区   
 40   readLocation=(readLocation   +   m_readsize)%m_buffer.Length;   
 41   //通知对象的第一个等待线程可以从WaitSleepJoin转换到Started状态.   
 42   Monitor.Pulse(this);   
 43   //返回给读取者取出的数值   
 44   return   newBuf;   
 45   }   
 46   }   
 47     
 48   //将数据放入缓冲区   
 49   public   void   setBuffer(byte[]   writeValue)   {   
 50   //锁住共享数据区   
 51   lock(this)   {   
 52   //如果缓冲区已满,那么进入waitsleepjoin状态   
 53   if(bufferCount==m_buffer.Length)   {   
 54   Console.WriteLine("缓冲区溢出!");   
 55   Monitor.Wait(this);   
 56   }   
 57   //向缓冲区写入数据   
 58   Buffer.BlockCopy(writeValue,   0,   m_buffer,   writeLocation,   m_readsize);   
 59   //自加,代表缓冲区现在到底有几个数据   
 60   bufferCount+=m_readsize;   
 61   //用%实现缓冲区的循环利用   
 62   writeLocation=(writeLocation   +   m_readsize)%m_buffer.Length;   
 63   //唤醒waitSleepJoin状态的进程,到started状态   
 64   Monitor.Pulse(this);   
 65   }//使用lock隐式的释放了共享锁   
 66   }   
 67   }   
 68     
 69       
 70     
 71       
 72   //写入者类,向缓冲区中放入数据   
 73   public   class   Writer   {     
 74   //定义了同步变量   
 75   FileBuffer   shared;   
 76   FileStream   file;   
 77   //此处构造函数的作用是在启动类中调用写入者的时候,把启动类中定义的sharedLocation传过来   
 78   public   Writer(FileBuffer   sharedLocation)   {   
 79   file   =   new   FileStream("C:\\Test.txt",FileMode.Open);   
 80   shared=sharedLocation;   
 81   }   
 82   //定义写入过程   
 83   public   void   Write()   {   
 84   //将数据放入缓冲区   
 85   Byte[]   datas   =   new   byte[1024];   
 86     
 87   for(int   byteread=0;byteread<=file.Length;byteread   +=   datas.Length)   {   
 88   file.Read(datas,   byteread,   datas.Length);   
 89   shared.setBuffer(datas);   
 90   }   
 91     
 92   file.Close();   
 93     
 94   //得到当前线程的名字   
 95   string   name=Thread.CurrentThread.Name;   
 96   //此线程执行完毕   
 97   Console.WriteLine(name+"done   writeing");   
 98   }   
 99   }   
100     
101   public   class   Reader   {//定义读取者   
102   byte[]   value;   
103   FileStream   file;   
104   //定义同步变量   
105   FileBuffer   shared;   
106   //定义构造函数,负责传递启动类中的shared   
107   public   Reader(FileBuffer   sharedLocation)   {   
108   file   =   new   FileStream("C:\\Data.txt",FileMode.Create);   
109   shared=sharedLocation;   
110   }   
111     
112   public   void   Read()   {   
113   //从缓冲区中循环读取   
114   for(int   bytewrite=0;bytewrite<=65535;)   {   
115   value=shared.getBuffer();   
116   file.Write(value,   bytewrite,   value.Length);   
117   bytewrite+=value.Length;   
118   }   
119     
120   file.Close();   
121     
122   //取得当前线程的名字   
123   string   name=Thread.CurrentThread.Name;   
124   Console.WriteLine(name+"done   reading");   
125   }   
126   }   
127     
128   public   class   ThreadTest   {   //设置为启动类   
129   public   static   void   Main()   {   
130   FileBuffer   shared=new   FileBuffer();   
131   //初始化了写入者和读取者,并且把shared参数传递了过去   
132   Writer   Writer1=new   Writer(shared);   
133   Reader   Reader1=new   Reader(shared);   
134     
135   Thread   WriterThread   =   new   Thread(new   ThreadStart   (Writer1.Write));   
136   WriterThread.Name="写入者";   
137     
138   Thread   ReaderThread   =   new   Thread(new   ThreadStart   (Reader1.Read));   
139   ReaderThread.Name="读取者";   
140   //启动这两个线程   
141   WriterThread.Start();   
142   ReaderThread.Start();   
143   WriterThread.Join();   
144   ReaderThread.Join();   
145   Console.ReadLine();   
146   }   
147   }   
148   }
149 
posted @ 2007-07-24 15:18  hq5460  阅读(193)  评论(0编辑  收藏  举报