FileStream锁定文件以进行读写

时间:2012-12-04 07:58:09

标签: c# multithreading locking filestream

我有以下代码块让我头疼。

逻辑上它应该工作,因为我使用在using语句中提供锁的文件流。当它到达创建StreamWriter的行时,它无法说“文件不可写”。

现在我的程序是一个多线程应用程序。任何线程都可能尝试写入此文件。我需要程序来锁定文件,读取内容,检查内容,然后回写任何更改。在此过程中,没有其他线程能够访问该文件。

using (var fs = File.Open(fileLoc, FileMode.Open, FileAccess.ReadWrite, FileShare.None))
{
    var sr = new StreamReader(fs);
    var str = sr.ReadToEnd();
    var strArray = str.Split(',');
    if (strArray.Any(st => st == text))
    {
        return;
    }
    sr.Close();

    var sw = new StreamWriter(fs);
    sw.Write(str + text);
    sw.Flush();
    sw.Close();
}

3 个答案:

答案 0 :(得分:8)

FileShare.None标志不会导致线程排队,它只是锁定文件,因此会获得异常。要提供互斥访问,您可以在写入之前锁定共享对象。

但你说这个“现在我的程序是一个多线程应用程序。任何线程都可能试图写入这个文件。”现在,这些线程是否都使用完全相同的方法写入文件?我们假设他们这样做,那么这应该有用......

创建一个静态类变量......

private static object lockObject = new object();

在这里使用......

lock (lockObject) 
{
    using(var sw = new StreamWriter(fs))
    {
       sw.Write(str + text);
    }
}

我已经对线程做了一些假设,所以如果这不起作用或者向我们提供更多信息,你可能需要查找有关同步的信息。

另外,请提前关闭StreamReader(如果方法先前返回)。使用后立即关闭它,或者更好地使用using

答案 1 :(得分:3)

答案 2 :(得分:1)

MSDN reference Close方法一样

  

关闭StreamReader对象和基础流,然后释放   与阅读器关联的任何系统资源。

因此,随后对StreamWriter的调用似乎无法使用封闭的资源,从而给您显示消息“文件不可写”。

尝试一下

            using (var fs = File.Open(path, FileMode.Open, FileAccess.ReadWrite, FileShare.None))
        {
            using (var sr = new StreamReader(fs))
            {
                var str = sr.ReadToEnd();
                // ...

                using (var sw = new StreamWriter(fs))
                {
                    // ...
                }
            }
        }