【问题标题】:IOException The process cannot access the file because it is being used by another process when using XDocumentIOException 进程无法访问该文件,因为在使用 XDocument 时它正被另一个进程使用
【发布时间】:2013-07-31 03:02:07
【问题描述】:

我不断收到一个 IOException,它无法访问该文件,因为它正被另一个进程使用。我想要做的是每次我正在查看的文件都被更改..它通过 TCP/IP 将其作为数组发送。我找不到任何关闭 XDocument 的方法,只是不知道如何解决这个错误……我用谷歌搜索,仍然找不到任何东西。任何帮助将不胜感激

编辑:我找到了文件阅读器和其他东西的其他解决方案.. 但使用 xdocument 时似乎有所不同

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

//filesystemwatcher
using System.IO;

//tcpip server
using System.Net;
using System.Net.Sockets;

//XML
using System.Xml;
using System.Xml.Linq;

namespace ChampSelect_FileWatcher
{
    class Program
    {
        //TCP IP variables
        public static Int32 port;
        public static IPAddress localAddr;
        public static TcpListener server;
        public static TcpClient client;
        public static NetworkStream stream;
        public static XDocument doc;


        public static void Main(string[] args)
        {
            //LOAD XML FILE
            doc = XDocument.Load("C:/Trio Scripts/example.xml");

            //OBSERVE FILE
            FileSystemWatcher watcher = new FileSystemWatcher();
            watcher.Path = @"C:\Trio Scripts";
            watcher.Filter = "example.xml";

            //watch for changes in LastWrite
            watcher.NotifyFilter = NotifyFilters.LastWrite;

            //event handler
            watcher.Changed += new FileSystemEventHandler(OnChanged);

            //Begin watching
            watcher.EnableRaisingEvents = true;


            //TCP IP SERVER
            try
            {
                Console.WriteLine("Waiting for 99150 to run...\n");
                //config TCP stuff
                port = 9905;
                localAddr = IPAddress.Parse("10.0.0.66");
                server = new TcpListener(localAddr, port);
                server.Start();
                client = server.AcceptTcpClient();
                stream = client.GetStream();
                Console.WriteLine("Connection to Viz successful!");
                Console.WriteLine("***LISTENING FOR CHANGES TO: " + watcher.Filter + "***\n");


            }
            catch (SocketException z)
            {
                Console.WriteLine("SocketException: {0}", z);
            }

            //prevent console from closing
            Console.ReadKey();
            Console.ReadKey();
            Console.ReadKey();
        }

        // Define the event handlers.
        private static void OnChanged(object source, FileSystemEventArgs e)
        {
            //reload xml file
            //doc = XDocument.Load("C:/Trio Scripts/example.xml");
            //doc.Root.ReplaceWith(XElement.Load("C:/Trio Scripts/example.xml"));

            XDocument doc;
            using (var reader = XmlReader.Create("C:/Trio Scripts/example.xml"))
            {
                doc = XDocument.Load(reader);
            }

            // Nodes in XML
            string[] bans = doc.Descendants("ban").OrderBy(element => Int32.Parse(element.Attribute("order").Value)).Select(element => element.Value).ToArray();

            // String to send the message on
            String sendMsg = "";

            // Proceed with reading XML
            for (int i = 0; i < bans.Length; i++)
                sendMsg += bans[i] + " ";

            byte[] msg = System.Text.Encoding.ASCII.GetBytes(sendMsg);
            stream.Write(msg, 0, msg.Length);
            Console.WriteLine("Change detected, sending changes to Viz");
            sendMsg = "";
        }
    }//end class
}//end namespace

【问题讨论】:

  • 您是否在代码中的任何位置使用"C:/Trio Scripts/example.xml" 文件?如果是的话也发帖
  • FileSystemWatcher.OnChanged 在文件更改时被调用。哪个文件?和example.xml有什么关系?
  • 更新了代码,让你们可以看到一切

标签: c# xml ioexception


【解决方案1】:

问题在于,每当文件更改时,您都会收到多个更改事件

在阅读更改后的文件之前,您应该稍等片刻。

您还应该使用e.FullPath 并检查

 e.ChangeType == WatcherChangeTypes.Changed

如果您无法打开文件,您应该稍后再试

【讨论】:

  • 嗯嗯,我们在几秒钟后手动更改文件,但它仍然给我们那个错误..就像输入几个字母..保存..然后它第一次工作..然后再次做同样的事情,然后我们得到那个错误
  • 永远不要在更改事件中对文件进行任何处理,启动一个处理更改的 System.Threading.Task。
  • sleep 命令在 10 秒似乎有效.. 但这并不能满足我们正在尝试做的事情。你能解释一下在我们的代码中在哪里使用 e.ChangeType == WatcherChangeTypes.Changed 吗?抱歉,我们是 C# 新手
  • 将尝试像您推荐的那样启动 System.Threading.Task,看看它是否有效...
  • 根据您的建议实现了多线程,并且成功了!
【解决方案2】:

您仍然可以使用XDocumentXmlReader

XDocument doc;
using (var reader = XmlReader.Create("C:/Trio Scripts/example.xml"))
{
    doc = XDocument.Load(reader);
}

using 块为阅读器完成时,文件句柄应该被关闭。

更新

也许XmlReader.Create(string) 的行为并没有以最小的方式打开文件。如果这是导致异常的原因,请尝试使用此更明确的代码指定文件权限:

XDocument doc;
using (var stream = File.Open("C:/Trio Scripts/example.xml", FileMode.Open, FileAccess.Read, FileShare.ReadWrite))
using (var reader = XmlReader.Create(stream))
{
    doc = XDocument.Load(reader);
}

【讨论】:

  • 作为 .net 开发人员,您应该对 using 语句非常熟悉,它的用途很多。
  • ^ torobot 我们是 C# 的新手,不幸的是,我们只是边学习边学习......他们只是把我们扔进去了
  • 也许代码的另一部分正在锁定您的文件,也许是检测文件何时发生更改的代码。
  • 哦,当它加载文件时在 main 中......我们将其注释掉了,它仍然给我们同样的错误
  • 试试我的更新。我不确定您收到的是哪一行的文件权限问题。这也可能会有所帮助(无论堆栈跟踪指向您发布的代码还是其他地方)。
猜你喜欢
  • 2018-09-20
  • 2020-03-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-11-18
  • 2021-12-02
  • 1970-01-01
  • 2010-12-10
相关资源
最近更新 更多