我一直在使用的一个应用程序在尝试序列化类型时失败了。

像这样的陈述

XmlSerializer lizer = new XmlSerializer(typeof(MyType));

生产:

System.IO.FileNotFoundException occurred
  Message="Could not load file or assembly '[Containing Assembly of MyType].XmlSerializers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null' or one of its dependencies. The system cannot find the file specified."
  Source="mscorlib"
  FileName="[Containing Assembly of MyType].XmlSerializers, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null"
  FusionLog=""
  StackTrace:
       at System.Reflection.Assembly._nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, Assembly locationHint, StackCrawlMark& stackMark, Boolean throwOnFileNotFound, Boolean forIntrospection)
       at System.Reflection.Assembly.nLoad(AssemblyName fileName, String codeBase, Evidence assemblySecurity, Assembly locationHint, StackCrawlMark& stackMark, Boolean throwOnFileNotFound, Boolean forIntrospection)

我没有为我的类定义任何特殊的序列化器。

我该如何解决这个问题?


当前回答

信不信由你,这是正常行为。抛出一个异常,但由XmlSerializer处理,因此如果忽略它,一切都应该继续正常进行。

我发现这非常烦人,如果你搜索一下,会有很多抱怨,但据我所知,微软并不打算对此采取任何措施。

如果关闭特定异常的第一次机会异常,就可以避免在调试时一直弹出异常。在Visual Studio中,打开调试->异常(或按Ctrl + Alt + E),公共语言运行时异常->系统。IO -> System.IO.FileNotFoundException。

您可以在博客文章c# XmlSerializer FileNotFound异常(其中讨论了Chris Sells的工具XmlSerializerPreCompiler)中找到关于另一种方法的信息。

其他回答

在Visual Studio项目属性(“Build”页面,如果我没记错的话)中有一个选项显示“生成序列化程序集”。尝试为生成[包含MyType的程序集]的项目打开该选项。

另一方面,对编译错误进行故障排除是非常复杂的。这些问题在FileNotFoundException异常中显示,并显示如下信息:

File or assembly name abcdef.dll, or one of its dependencies, was not found. File name: "abcdef.dll"
   at System.Reflection.Assembly.nLoad( ... )
   at System.Reflection.Assembly.InternalLoad( ... )
   at System.Reflection.Assembly.Load(...)
   at System.CodeDom.Compiler.CompilerResults.get_CompiledAssembly() 

You may wonder what a file not found exception has to do with instantiating a serializer object, but remember: the constructor writes C# files and tries to compile them. The call stack of this exception provides some good information to support that suspicion. The exception occurred while the XmlSerializer attempted to load an assembly generated by CodeDOM calling the System.Reflection.Assembly.Load method. The exception does not provide an explanation as to why the assembly that the XmlSerializer was supposed to create was not present. In general, the assembly is not present because the compilation failed, which may happen because, under rare circumstances, the serialization attributes produce code that the C# compiler fails to compile.

请注意 当XmlSerializer在不能访问临时目录的帐户或安全环境下运行时,也会发生此错误。

来源: http://msdn.microsoft.com/en-us/library/aa302290.aspx

Martin Sheburn最初的回答是正确的。 来自edeboursetty, tomas-kubes)的代码示例,quadfinity应该解决在调试器中不引发过量异常的问题。

这里有一个简短的解决方案:

internal sealed static class XmlSerializerHelper
{
    private static readonly ConcurrentDictionary<Type, System.Xml.Serialization.XmlSerializer> s_xmlSerializers = new();

    public static System.Xml.Serialization.XmlSerializer Get<T>()
    {
        return s_xmlSerializers.GetOrAdd(typeof(T), _ => System.Xml.Serialization.XmlSerializer.FromTypes(new [] {typeof(T)})[0]);
    }
}

信不信由你,这是正常行为。抛出一个异常,但由XmlSerializer处理,因此如果忽略它,一切都应该继续正常进行。

我发现这非常烦人,如果你搜索一下,会有很多抱怨,但据我所知,微软并不打算对此采取任何措施。

如果关闭特定异常的第一次机会异常,就可以避免在调试时一直弹出异常。在Visual Studio中,打开调试->异常(或按Ctrl + Alt + E),公共语言运行时异常->系统。IO -> System.IO.FileNotFoundException。

您可以在博客文章c# XmlSerializer FileNotFound异常(其中讨论了Chris Sells的工具XmlSerializerPreCompiler)中找到关于另一种方法的信息。

为了避免异常,你需要做两件事:

向序列化类添加属性(我希望您有访问权限) 使用sgen.exe生成序列化文件

将System.Xml.Serialization.XmlSerializerAssembly属性添加到类中。 将'MyAssembly'替换为MyClass所在程序集的名称。

[Serializable]
[XmlSerializerAssembly("MyAssembly.XmlSerializers")]
public class MyClass
{
…
}

使用sgen.exe实用程序生成序列化文件,并将其与类的程序集一起部署。

' sgen.exe MyAssembly.dll '将生成文件myassembly . xmlserializer .dll

这两个更改将导致.net直接查找程序集。 我检查了一下,它在。net框架3.5和Visual Studio 2008上工作