【问题标题】:Merge .dll into C# Assembly?将 .dll 合并到 C# 程序集中?
【发布时间】:2011-05-20 09:34:38
【问题描述】:

使用#C.net 3.5

我知道 ILMerge 和类似技术,但我实际上想使用 Jeffrey Richter's suggestions

将此代码添加到构造函数后,命名空间出现问题。

杰弗里·里希特的代码:

AppDomain.CurrentDomain.AssemblyResolve += (sender, args) => {
    String resourceName = "AssemblyLoadingAndReflection." + new AssemblyName(args.Name).Name + ".dll";
    using (var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName)) {
        Byte[] assemblyData = new Byte[stream.Length];
        stream.Read(assemblyData, 0, assemblyData.Length);
        return Assembly.Load(assemblyData);
    }
};

我将这两个 DLL 设置为“嵌入式资源”并将它们添加为参考,但是当我构建程序时,这两个 dll 仍然“未嵌入”,然后我将它们作为参考删除,但是当我构建时程序有错误提示:“找不到类型或命名空间......您是否缺少 using 指令或程序集引用?”我将两个命名空间添加为 using 指令...,然后我尝试删除两个引用和两个 using 指令,但仍然出现错误。

这是我的代码:

using System.Reflection;
    namespace WindowsFormsApplication2
    {
        public partial class Ndice : Form
        {
            public Ndice()
            {
                AppDomain.CurrentDomain.AssemblyResolve += (sender, args) =>
                {
                    String resourceName = "AssemblyLoadingAndReflection." + new AssemblyName(args.Name).Name + ".dll";
                    using (var stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName))
                    {
                        Byte[] assemblyData = new Byte[stream.Length];
                        stream.Read(assemblyData, 0, assemblyData.Length);
                        return Assembly.Load(assemblyData);
                    }
                };
                InitializeComponent();
               }
           }
        }

【问题讨论】:

  • 你理解你粘贴的代码吗?它完全符合您的要求。
  • 是“AssemblyLoadingAndReflection”。应该改变?如果是这样怎么办?
  • 您的原始代码很接近,但里面有硬编码的 exe 名称。请参阅下面的答案

标签: c# dll embed


【解决方案1】:

把它放在构造函数中,而不是 InitializeComponent()。向主类源代码文件添加 using 指令不是问题。

【讨论】:

    【解决方案2】:

    根据您问题中的描述,可能需要回答一些问题:

    1. 究竟是什么不工作?您是在编译时失败还是在运行时失败?
    2. 能否显示无法编译或在运行时无法运行的代码?
    3. 您所说的程序集“未嵌入”是什么意思?

    基本上,据我了解,您的代码尝试使用 2 个程序集中的类。这段代码是静态的,意味着类必须在编译时知道。或者换句话说,您必须引用这两个程序集才能编译使用其中定义的类型的代码。

    当您添加这些程序集作为参考时,我真的不明白出了什么问题。如果让您感到困扰的是您看到它们被复制到 bin/debug 目录中,那仍然不应该阻止它们也被嵌入到您的主程序集中。因此,为了测试,您可以尝试从 bin/debug 中手动删除它们,或者将它们设置为“copy local = false”。

    还有一件事 - 您遇到的提到“使用”和“命名空间”的错误实际上与命名空间无关。这个错误意味着编译器没有找到它需要的类型。这可能是因为您删除了对 2 个程序集的引用。

    【讨论】:

    • 谢谢,您的指点帮助我弄清楚了,在发布应用程序文件下的属性区域中,它默认包含它们。
    • 运行程序并尝试使用 dll 后,我得到:无法加载文件或程序集 'Assembly1231,Version=0.9.6.8,Culture=neutral,PublicKeyToken=null' 或其依赖项之一。无效指针(HRESULT 异常:0x80004003 (E_POINTER))
    【解决方案3】:
    String resourceName = "AssemblyLoadingAndReflection." + new AssemblyName(args.Name).Name + ".dll";
    

    应该改为:

    String resourceName = Application.Current.GetType().Namespace + "." + new AssemblyName(args.Name).Name + ".dll";
    

    【讨论】:

    • Application.Current 不存在?你是说 CurrentCulture 吗?
    猜你喜欢
    • 2011-06-05
    • 2010-09-09
    • 2013-08-03
    • 1970-01-01
    • 1970-01-01
    • 2018-03-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多