【问题标题】:Qn: Getting Around Windows File Lockup Property -- using FileHandling in Java or C#Qn:绕过 Windows 文件锁定属性——在 Java 或 C# 中使用文件处理
【发布时间】:2012-02-23 20:48:27
【问题描述】:

我在为我的企业开发软件时遇到了问题。我要完成的任务是,我需要在另一个程序不断访问该文件时更新一个文件 (.txt)。

最终的设置是这样的:我将运行一个软件,不断读取提要文件的内容(称为 info.txt)。我正在运行另一个脚本,不断更新提要文件 (info.txt)。

在实现上述设置后,我意识到使用该文件的严重冲突。随着软件(称为 AAA)的运行,我什至无法手动编辑 info.txt。我打开 info.txt,进行更改,然后单击保存,Windows 返回错误消息:“该进程无法访问该文件,因为它正在被另一个进程使用。”如果我尝试删除 info.txt,错误消息是“无法完成操作,因为文件在 AAA.exe 中打开”。 当我运行不断更新 info.txt 的 (java) 脚本时,文件 IO 异常为:java.io.FileNotFoundException: info.txt(该进程无法访问该文件,因为它正在被另一个进程使用)

软件 AAA 的开发不是很好。 (它对我的企业来说是一个外国软件,所以我不能修改它的行为/源代码。)它访问文件的方式完全锁定了文件。我想暂时在软件的配置文件中指出对 info.txt 的引用以允许临时编辑,但是这种方法会失败,因为在运行 AAA 的情况下(我需要它),我无法对任何文件进行任何更改它正在使用。

我咨询了软件 AAA 的主要开发商之一。他承认现在这是一个问题,他会在下一个版本中改进它。但与此同时,我希望设置能够正常工作。他告诉我他使用 .NET 进行编程,并提供了一条可以帮助我解决问题的代码:

FileStream fs = new FileStream(@"info.txt", FileMode.OpenOrCreate, FileAccess.Write, FileShare.ReadWrite);

据推测,通过提供这些参数,此文件流可以在写入和读取时共享。

我是一名 Java 程序员,我没有使用过 .NET 的经验。但是我做了一些研究和学习,我意识到他的代码是C#的语法,它运行在.NET框架的CLR中。我在我的电脑上设置了 C# 并学习了一些 C# 初学者教程,并提出了以下脚本,希望能解决我的问题。

如果 C# 确实允许从根本上更改文件的访问属性,我会打开 info.txt 的文件流,允许读写共享它。一旦我这样做了,我就可以运行我的更新 info.txt 的脚本,然后运行不断刷新 info.txt 的软件 AAA。

为了实现上面的实现,我想出了一个C#脚本:

================================================ =

using System;
using System.IO;

class CopyFeed
{
    static void Main()
    {
        string fileName1 = "info.txt";  
        string fileName2 = "info2.txt";


        FileStream fs = new FileStream(@fileName1, FileMode.OpenOrCreate,             FileAccess.Write, FileShare.ReadWrite);
        StreamWriter sw = null;

        // attempting to unlock part of the file, didn't work
        /*
        string contents = File.ReadAllText(@fileName2);
        fs.Unlock(0, contents.Length * 2);
        */

        while (true)
        {
            Console.WriteLine("Copying Feed...");

            string contents = File.ReadAllText(@fileName2);

            try
            {
                sw = new StreamWriter(fs);
                sw.Write(contents);
            }
            catch (Exception e)
            {
                Console.WriteLine("CopyFeed :: " + e.Message);
            }
            finally
            {
                if (sw != null)
                {

                    sw.Flush();
                    //sw.Close();

                }
            }

            Console.WriteLine("Pausing For 2 sec...");
            System.Threading.Thread.Sleep(2000);

        }



    }
}

================================================ =

据说,我会让我的 java 脚本不断更新 info2.txt 。然后我会让这个 C# 脚本不断地将 info2.txt 的全部内容复制到 info.txt 中。 我希望从两个方面寻求帮助:

  1. 上面的脚本仍然有问题,因为它所做的只是不断地追加到文件 info.txt。我希望找到一种方法,可以在每次迭代开始时清除文件的内容,然后复制 file2 的内容。现在如果我执行脚本,它会随着时间的推移创建一个无限大的文件。

  2. 根据上面的描述,我的解决方案是否可行?我有更好的选择吗? (软件 AAA 行为保持不变)有没有办法绕过它?

  3. 我能找到使用 Java 的解决方案吗? Java 是否具有文件处理能力,可以在更基础的层面上与 Windows 系统交互并解锁文件?

过去几天我一直在解决这个问题,但我真的陷入了困境。我真诚地感谢任何提供任何见解的人!

【问题讨论】:

  • 只有您知道解决方案是否有效...您是否测试/调试过您当前拥有的代码..???
  • 嗨 DJ Kraze,我试过了,但调试失败。这是我希望寻求的帮助之一。一般来说,我对 C# 和文件处理几乎没有经验。我不知道如何让我的 C# 脚本在那里运行。在再次写入/复制之前,我需要一种清除文件内容的方法。

标签: c# java windows file-handling


【解决方案1】:

我无法告诉你你描述的方法是否适用于访问锁定的文件,因为我没有这样的场景可供测试。

至于你的问题1。):

您可以使用静态方法File.WriteAllText(命名空间System.IO)清除文件的内容。这相当于

string contents = File.ReadAllText(@fileName2);

在您发布的 C# 代码中。

例子:

System.IO.File.WriteAllText(@"C:\Test\test.txt", "");

或更好

System.IO.File.WriteAllText(@"C:\Test\test.txt", string.Empty);

或者,您可以使用值为 0 的 FileStream 的 setLength 方法:

fs.SetLength(0);

【讨论】:

    【解决方案2】:

    虽然您的方法可以防止在您的程序上发生 FileNotFoundException,但您应该考虑对尝试访问您正在编辑的文件的其他程序导致相同异常的可能性。

    我的工作有一个类似的用例,我们直接与版本控制而不是文件进行交互。这样,如果正在进行并发编辑,我们可以合并更改。

    如果您不习惯这种方法,您至少应该更改代码以捕获 System.IO.FileNotFoundExceptions 而不是 System.Exception。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2010-10-25
      • 1970-01-01
      • 2016-06-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多