了解Managed C ++
我在理解托管C ++如何工作和编译时遇到困难。
在.NET Framework中,您可以使用C#/ VB / F#/ ..等开发代码。 并且所有这些语言都将被编译为与Java字节码相似的通用中间语言(CIL)。 从理论上讲,CIL可以安装在任何平台上(Mono使其具有实用性)。 在Windows上,CLR将CIL编译为本地代码Just-In-Time(JIT),并且一切运行顺利并且顺利。
现在,Managed C ++如何编译? 它是否编译为CIL代码并等待CLR使用JIT运行它? 我认为不是,因为Managed C ++可以使用标准C ++代码(不会编译为CIL)。 此外,它如何能够使用.NET程序集(即CIL)?
我将不胜感激任何帮助。 谢谢
编辑:
我看到了这个答案。 它指出,在C ++ / CLI中,托管代码被编译为MSIL,并且您可以选择将非托管代码编译为本机代码或MSIL。 因此,我现在明白如何调用.NET程序集。
无论如何,如果非托管代码被编译为本地代码,我仍然不明白C ++非托管代码如何在同一程序集中的托管代码上运行。 有任何想法吗?
这是一个非常严格的实施细节的大话题。 很难解决所有问题,但这个问题存在一些误解。 让我们来解决这些问题,可能有助于进入下一个阶段。
此外,它如何能够使用.NET程序集(即CIL)?
不仅仅是CIL,链接器会生成混合模式程序集。 包含.NET元数据+ msil和本机代码。 实际上,就OS加载器而言,它是可执行文件中的正常代码。 与本机C ++编译器生成的类型没有什么不同。 它被加载并重新定位,就像纯原生可执行映像一样。 这是.NET元数据+ MSIL是古怪的。 对于加载器来说,它看起来像是一大块数据,根本不会触及它。 只有CLR可以。
...使用标准C ++代码(不编译到CIL)
不太准确,原生C ++代码可以编译为msil或机器代码。 你得到的东西取决于/ clr编译选项是否被使用,或者在功能级别管理的#pragma是否有效。 CIL并没有比较好,比如在Java JVM中使用的字节码。 它功能更强大,可以支持任何C ++ 03兼容的本地C ++代码。 有时候你会这样做,以便利用反向拼写(本地代码调用托管代码)。 有时它是偶然完成的,并且完全太多本机C ++代码被编译为msil。 由抖动产生的机器码不是最优的(它在时间限制下优化)并且不以任何方式进行管理。 这是无法验证的,并没有得到垃圾收集者的喜爱。
CIL的最佳心理图像是在前端(解析器)和后端(代码生成器和优化器)之间的任何本地C ++编译器中使用的中间代表。 通常是一个不可见的实现细节,但在使用使用LLVM的C ++编译器时(如Clang所做的那样)会更明显。 .NET即时编译器在运行时会在编译时执行LLVM的工作。
当托管代码调用本机代码时(或其他方式),大多数程序员都会在巨型模式切换时引发心理图像。 这根本不准确。 您可能想看看这篇文章,展示了C ++编译器后端生成的机器代码与抖动之间的区别。 关键是它几乎完全相同,这是确保托管代码与本机代码竞争的基本特征。 有助于阐明调用本地代码的托管代码或其他方式如何不那么特别。
另一个误解是托管代码自动更安全。 并非如此,像C#这样的语言可以让你用指针进行派对,并像在C ++中一样在堆栈中乱写,并且可以像这样轻松地破坏内存。 它只是更好的分区,它会强制你用unsafe
关键字来明确它。 对C ++ / CLI没有这样的限制,什么都行。
托管代码和本地代码之间的本质区别是编译msil时抖动产生的数据结构。 额外的数据,你不会从本地编译器。 该数据是垃圾收集器所需的,它告诉它如何找回对象根。 更多关于这篇文章中的数据。 不得不遵守这些数据并允许GC完成工作,这使得托管代码在运行时慢了一点。
Manged C ++已弃用。 今天要编写本地C ++和Manged代码,您需要使用C ++ CLI。 它符合CLR,它可以运行其他.net程序集。 您也可以使用本机调用,这对于本机代码和.NET代码之间的互操作性非常好。要调用.NET Assembly,请在您的项目中向该Assembly添加引用并添加代码:
using namespace System;
链接地址: http://www.djcxy.com/p/85419.html
上一篇: Understanding of Managed C++
下一篇: Is Boost/STL slow with regard to high performance computing?